I'm making a dictionary application, which has a search function. When we type something to the textfield, we want receive a list result in the JList instantly, but I can't make it has been done instantly, always has latency, maybe 50ms.
Meanwhile I'm using another application, which can do it with 0ms latency. You can see it there: video
I'm using prefix tree. Here is my code:
Dictionary trie to search words.
// I have another arraylist **dictionary** contains all words
// you can see attribute **count** in DictionaryTrie, and **index** in Node
// You can see that: I use Trie to find index, and I use index to receive a list through dictionary
public class DictionaryTrie {
private final Node root;
private static int count;
private static ArrayList<Word> dictionary;
public DictionaryTrie() {
count = 0;
root = new Node(count);
dictionary = Dictionary.getInstance().getDictionary();
}
public void insert(Word newWord) {
String word = newWord.getWordTarget();
Node currentNode = root;
for (int i = 0; i < word.length(); i++) {
char c = word.charAt(i);
Node node = currentNode.children.get(c);
if (node == null) {
node = new Node(count);
currentNode.children.put(c, node);
}
currentNode = node;
}
count++;
}
public ArrayList<Word> search(String word) {
ArrayList<Word> list = new ArrayList<Word>();
Node currentNode = root;
for (int i = 0; i < word.length(); i++) {
char c = word.charAt(i);
Node node = currentNode.children.get(c);
if (node == null) {
return null;
}
currentNode = node;
}
int start = currentNode.index;
for (int i = start; i < Math.min(dictionary.size(), start + 15); i++) {
list.add(dictionary.get(i));
}
return list;
}
private class Node {
public Map<Character, Node> children;
public int index;
public Node(int idx) {
children = new HashMap<Character, Node>();
index = idx;
}
}
}
Dictionary Management:
public class DictionaryManagement {
private static DictionaryManagement instance;
private static Dictionary dict;
private static ArrayList<Word> listWord;
private static DictionaryTrie dictionaryTrie;
ConnectJDBC connectJDBC;
Connection conn;
private DictionaryManagement() {
dict = Dictionary.getInstance();
listWord = dict.getDictionary();
dictionaryTrie = new DictionaryTrie();
}
public static DictionaryManagement getInstance() {
if (instance == null) {
instance = new DictionaryManagement();
}
return instance;
}
public ArrayList<Word> searchWord(String word) {
return dictionaryTrie.search(word);
}
}
Search controller
public class SearchController{
private ListWord listWord;
private JTextField searchField;
private DictionaryManagement dictionaryManagement;
public SearchController(ListWord list, JTextField field) {
dictionaryManagement = DictionaryManagement.getInstance();
this.listWord = list;
this.searchField = field;
this.searchField.addKeyListener(new SearchFieldListener());
}
private void search(String string) {
ArrayList<Word> list = dictionaryManagement.searchWord(string);
listWord.removeItem();
if (list != null) {
listWord.addItem(list);
}
listWord.setSelectedIndex(-1);
}
private class SearchFieldListener implements KeyListener{
@Override
public void keyTyped(KeyEvent e) {
}
@Override
public void keyPressed(KeyEvent e) {
}
@Override
public void keyReleased(KeyEvent e) {
String text = searchField.getText();
search(text);
}
}
}
Main
searchController = new SearchController(listWord, searchField);
I think I have no problem with my algorithm.