1 package com.hughes.android.dictionary;
\r
3 import java.io.IOException;
\r
4 import java.io.RandomAccessFile;
\r
5 import java.util.ArrayList;
\r
6 import java.util.Comparator;
\r
7 import java.util.List;
\r
8 import java.util.concurrent.atomic.AtomicBoolean;
\r
10 import com.hughes.util.CachingList;
\r
11 import com.hughes.util.raf.FileList;
\r
12 import com.hughes.util.raf.RAFFactory;
\r
13 import com.hughes.util.raf.RAFSerializable;
\r
14 import com.hughes.util.raf.RAFSerializableSerializer;
\r
15 import com.hughes.util.raf.RAFSerializer;
\r
16 import com.hughes.util.raf.UniformFileList;
\r
18 public final class Dictionary implements RAFSerializable<Dictionary> {
\r
20 static final RAFSerializer<Entry> ENTRY_SERIALIZER = new RAFSerializableSerializer<Entry>(
\r
22 static final RAFSerializer<Row> ROW_SERIALIZER = new RAFSerializableSerializer<Row>(
\r
24 static final RAFSerializer<IndexEntry> INDEX_ENTRY_SERIALIZER = new RAFSerializableSerializer<IndexEntry>(
\r
25 IndexEntry.RAF_FACTORY);
\r
27 final List<Entry> entries;
\r
28 final Language[] languages = new Language[2];
\r
30 public Dictionary(final String lang0, final String lang1) {
\r
31 languages[0] = new Language(lang0, Entry.LANG1);
\r
32 languages[1] = new Language(lang1, Entry.LANG2);
\r
33 entries = new ArrayList<Entry>();
\r
36 public Dictionary(final RandomAccessFile raf) throws IOException {
\r
37 entries = CachingList.create(FileList.create(raf, ENTRY_SERIALIZER, raf
\r
38 .getFilePointer()), 10000);
\r
39 languages[0] = new Language(raf, Entry.LANG1);
\r
40 languages[1] = new Language(raf, Entry.LANG2);
\r
43 public void write(RandomAccessFile raf) throws IOException {
\r
44 FileList.write(raf, entries, ENTRY_SERIALIZER);
\r
45 languages[0].write(raf);
\r
46 languages[1].write(raf);
\r
49 final class Language implements RAFSerializable<Language> {
\r
51 final String symbol;
\r
52 final List<Row> rows;
\r
53 final List<IndexEntry> sortedIndex;
\r
54 final Comparator<String> comparator = EntryFactory.entryFactory
\r
55 .getEntryComparator();
\r
57 Language(final String symbol, final byte lang) {
\r
59 this.symbol = symbol;
\r
60 rows = new ArrayList<Row>();
\r
61 sortedIndex = new ArrayList<IndexEntry>();
\r
64 Language(final RandomAccessFile raf, final byte lang) throws IOException {
\r
66 symbol = raf.readUTF();
\r
67 rows = CachingList.create(UniformFileList.create(raf, ROW_SERIALIZER, raf
\r
68 .getFilePointer()), 10000);
\r
69 sortedIndex = CachingList.create(FileList.create(raf,
\r
70 INDEX_ENTRY_SERIALIZER, raf.getFilePointer()), 10000);
\r
73 public void write(final RandomAccessFile raf) throws IOException {
\r
74 raf.writeUTF(symbol);
\r
75 UniformFileList.write(raf, rows, ROW_SERIALIZER, 4);
\r
76 FileList.write(raf, sortedIndex, INDEX_ENTRY_SERIALIZER);
\r
79 String rowToString(final Row row) {
\r
80 return row.isToken() ? sortedIndex.get(row.getIndex()).word : entries
\r
81 .get(row.getIndex()).toString();
\r
84 int lookup(String word, final AtomicBoolean interrupted) {
\r
85 word = word.toLowerCase();
\r
88 int end = sortedIndex.size();
\r
89 while (start < end) {
\r
90 final int mid = (start + end) / 2;
\r
91 if (interrupted.get()) {
\r
94 final IndexEntry midEntry = sortedIndex.get(mid);
\r
96 final int comp = comparator.compare(word, midEntry.word.toLowerCase());
\r
99 while (result > 0 && comparator.compare(word, sortedIndex.get(result - 1).word.toLowerCase()) == 0) {
\r
101 if (interrupted.get()) {
\r
106 } else if (comp < 0) {
\r
116 public static final class Row implements RAFSerializable<Row> {
\r
119 public Row(final int index) {
\r
120 this.index = index;
\r
123 static final RAFFactory<Row> RAF_FACTORY = new RAFFactory<Row>() {
\r
124 public Row create(RandomAccessFile raf) throws IOException {
\r
125 return new Row(raf.readInt());
\r
129 public void write(RandomAccessFile raf) throws IOException {
\r
130 raf.writeInt(index);
\r
133 boolean isToken() {
\r
137 public int getIndex() {
\r
145 public static final class IndexEntry implements RAFSerializable<IndexEntry> {
\r
147 final int startRow;
\r
149 public IndexEntry(final String word, final int startRow) {
\r
151 this.startRow = startRow;
\r
154 static final RAFFactory<IndexEntry> RAF_FACTORY = new RAFFactory<IndexEntry>() {
\r
155 public IndexEntry create(RandomAccessFile raf) throws IOException {
\r
156 final String word = raf.readUTF();
\r
157 final int startRow = raf.readInt();
\r
158 return new IndexEntry(word, startRow);
\r
162 public void write(final RandomAccessFile raf) throws IOException {
\r
163 raf.writeUTF(word);
\r
164 raf.writeInt(startRow);
\r
168 public String toString() {
\r
169 return word + "@" + startRow;
\r