【问题标题】:How to implement Autocomplete using Trie with a HashMap?如何使用带有 HashMap 的 Trie 实现自动完成?
【发布时间】:2020-07-24 07:43:49
【问题描述】:

下面是Trie的HashMap实现代码。但我不确定如何实现自动完成部分。我看到人们如何使用 LinkedList 来实现 Trie,但我想用 HashMap 来理解。任何帮助表示赞赏。我已经为我的 Trie 粘贴了下面的代码。

有没有办法查找前缀,然后转到前缀的末尾并查找其子项并将它们作为字符串返回?如果是这样,如何实现使用 HashMap 实现。或者我什至不应该使用 HashMap 并使用 LinkedList。而且我不确定,为什么一个比另一个更好?

public class TrieNode {

    Map<Character, TrieNode> children;
    boolean isEndOfWord;

    public TrieNode() {
        isEndOfWord = false;
        children = new HashMap<>();
    }

}

public class TrieImpl {

    private TrieNode root;

    public TrieImpl() {
        root = new TrieNode();
    }

    // iterative insertion into Trie Data Structure
    public void insert(String word) {
        if (searchTrie(word))
            return;

        TrieNode current = root;
        for(int i=0; i<word.length(); i++) {
            char ch = word.charAt(i);
            TrieNode node = current.children.get(ch);
            if(node == null) {
                node = new TrieNode();
                current.children.put(ch, node);
            }
            current = node;
        }
        current.isEndOfWord = true;
    }

    // search iteratively
    public boolean searchTrie(String word) {
        TrieNode current = root;
        for(int i=0; i < word.length(); i++) {
            char ch = word.charAt(i);
            TrieNode node = current.children.get(ch);
            if(node == null) {
                return false;
            }
            current = node;
        }
        return current.isEndOfWord;
    }


    // delete a word recursively
    private boolean deleteRecursive(TrieNode current, String word, int index) {

        if(index == word.length()) {
            if(!current.isEndOfWord) {
                return false;
            }
            current.isEndOfWord = false;
            return current.children.size() == 0;
        }
        char ch = word.charAt(index);
        TrieNode node = current.children.get(ch);

        if(node == null) {
            return false;
        }

        boolean shouldDeleteCurrentNode = deleteRecursive(node, word, index+1);

        if(shouldDeleteCurrentNode) {
            current.children.remove(ch);
            return current.children.size() == 0;
        }

        return false;
    }

    // calling the deleteRecursively function
    public boolean deleteRecursive(String word) {
        return deleteRecursive(root, word, 0);
    }

    public static void main(String[] args) {

        TrieImpl obj = new TrieImpl();

        obj.insert("amazon");
        obj.insert("amazon prime");
        obj.insert("amazing");
        obj.insert("amazing spider man");
        obj.insert("amazed");
        obj.insert("alibaba");
        obj.insert("ali express");
        obj.insert("ebay");
        obj.insert("walmart");

        boolean isExists = obj.searchTrie("amazing spider man");
        System.out.println(isExists);
    }
}

【问题讨论】:

    标签: java data-structures autocomplete hashmap trie


    【解决方案1】:

    我急于在这里找到其他解决方案,但这是 有趣的问题。

    回答这个问题-

    有没有办法查找前缀,然后到前缀的末尾 并寻找它的孩子并将它们作为字符串返回?

    是的,为什么不呢,如果你有前缀 ama ,现在转到你的 searchTrie 方法,当你完成并退出循环。然后,您有 current 变量指向 aama 的最后一个字符)

    然后您可以编写如下方法 -

        public List<String> getPrefixStrings(TrieNode current){
               // DO DFS here and put all character with isEndOfWord = true in the list
               // keep on recursing to this same method and adding to the list
               // then return the list
    
        }
    

    【讨论】:

    • 谢谢@anubhs,我会尝试这种方法。
    猜你喜欢
    • 2011-06-28
    • 1970-01-01
    • 1970-01-01
    • 2016-05-06
    • 1970-01-01
    • 2010-10-03
    • 2011-07-19
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多