簡単な入れ子構造を扱う #18
索引は0個以上の重複のない索引項目の並びであり、
索引項目は項目名と位置情報リストから成り、
位置情報リストは1個以上の重複のない位置情報の並びである。
項目名と位置情報はそれぞれがある順序集合の元であり、
索引における索引項目の並びは項目名によって順序付けられ、
位置情報リストは位置情報によってその並びが順序付けられる。
重複を許さないとは同順位の要素を各並びが2個以上持たないということである。
Index.java
package index; import java.util.Set; import java.util.TreeMap; public class Index<N extends Comparable<N>, L extends Comparable<L>> { private final TreeMap<N, Item<N, L>> items = new TreeMap<N, Item<N, L>>(); public boolean add(N name, L location) { Item<N, L> i = items.get(name); if (i == null) { items.put(name, new Item<N, L>(name, location)); return true; } else { return i.add(location); } } public Set<N> getNames() { return items.keySet(); } public Set<L> getLocations(N name) { Item<N, L> i = items.get(name); if (i == null) return null; return i.get(); } }
Item.java
package index; import java.util.Set; import java.util.TreeSet; class Item<N, L extends Comparable<L>> { private final N name; private final TreeSet<L> locations = new TreeSet<L>(); Item(N name, L location) { if (name == null) throw new IllegalArgumentException("null name"); if (location == null) throw new IllegalArgumentException("null location"); this.name = name; locations.add(location); } boolean add(L location) { return locations.add(location); } Set<L> get() { return locations; } }
IndexMaker.java
import index.Index; import java.util.Iterator; public class IndexMaker { public static void main(String[] args) { Index<String, Integer> i = new Index<String, Integer>(); i.add("interface", 46); i.add("abstract", 43); i.add("while", 12); i.add("default", 104); i.add("strictfp", 79); i.add("goto", 4); i.add("interface", 22); i.add("default", 53); show(i); for (Iterator<String> it = i.getNames().iterator(); it.hasNext(); ) { String n = it.next(); if (n.equals("goto")) { it.remove(); } else { boolean b = false; for (Iterator<Integer> itr = i.getLocations(n).iterator(); itr.hasNext(); ) { itr.next(); if (b) itr.remove(); else b = true; } } } System.out.println("--- remove \"goto\" and pages except first coming"); show(i); } private static void show(Index<String, Integer> index) { java.util.Set<String> ns = index.getNames(); int m = -1; for (String n : ns) { int l = n.length(); if (l > m) m = l; } StringBuilder s = new StringBuilder(); for (String n : ns) { s.append(n); for (int i = n.length(); i <= m; i++) s.append(' '); for (int p : index.getLocations(n)) s.append(p).append(' '); s.deleteCharAt(s.length() - 1); System.out.println(s); s.setLength(0); } } }