A graspable recursive solution using Trie
\nclass Solution {\n    class TrieNode{\n        StringBuilder sb;\n        Map<String, TrieNode> children;\n        \n        public TrieNode(){\n            s
```\nclass Solution {\n    class TrieNode{\n        StringBuilder sb;\n        Map<String, TrieNode> children;\n        \n        public TrieNode(){\n            sb = new StringBuilder();\n            children = new HashMap<>();\n        }\n    }\n    \n    public List<List<String>> deleteDuplicateFolder(List<List<String>> paths) {\n        TrieNode root = new TrieNode();\n        for(List<String> path: paths){\n            TrieNode curr = root;\n            \n            for(String node: path){\n                if(!curr.children.containsKey(node)){\n                    curr.children.put(node, new TrieNode());\n                }\n                \n                curr = curr.children.get(node);\n            }\n        }\n        \n        Map<String, Integer> freq = new HashMap<>();\n        encode(root, freq);\n        List<List<String>> res = new ArrayList<>();\n        List<String> path = new ArrayList<>();\n        dfs(root, freq, res, path);\n        return res;\n    }\n    \n\t/* \n\t\tEncodes the folders and stores their occurence count in a frequency map\n\t\te.g.: \n\t\t\t\tpaths: [["a"],["c"],["d"],["a","b"],["c","b"],["d","a"]]\n\t\t\t\tfreq: {"b()":2,"a()":1,"a(b())c(b())d(a())":1}\n\t*/\n\t\n    private void encode(TrieNode root, Map<String, Integer> freq){\n        if(root.children.isEmpty()){\n            return;\n        }\n        \n        List<String> list = new ArrayList<>();\n        for(Map.Entry<String, TrieNode> entry: root.children.entrySet()){\n            String folder = entry.getKey();\n            TrieNode child = entry.getValue();\n            encode(child, freq);\n            list.add(folder + "(" + child.sb.toString() + \')\');\n        }\n        \n        Collections.sort(list);\n        \n        for(String str: list){\n            root.sb.append(str);\n        }\n        \n        String serialStr = root.sb.toString();\n        freq.put(serialStr, freq.getOrDefault(serialStr, 0) + 1);\n    }\n    \n\t/*\n\t\tA simple DFS to discard the folders whose frequency of occurence is greater than 1\n\t*/\n\t\n    private void dfs(TrieNode root, Map<String, Integer> freq, List<List<String>> res, List<String> path){\n        if(freq.getOrDefault(root.sb.toString(), 0) > 1){\n            return;\n        }\n        \n        if(!path.isEmpty()){\n            res.add(new ArrayList<>(path));\n        }\n        \n        for(Map.Entry<String, TrieNode> entry: root.children.entrySet()){\n            String folder = entry.getKey();\n            TrieNode child = entry.getValue();\n            path.add(folder);\n            dfs(child, freq, res, path);\n            path.remove(path.size() - 1);\n        }\n    }\n}\n```
['Depth-First Search', 'Trie', 'Recursion']