Word Search II

http://www.lintcode.com/en/problem/word-search-ii/

package com.LintCode.Word;

import java.util.ArrayList;
import java.util.List;

public class Solution {
    /**
     * @param board: A list of lists of character
     * @param words: A list of string
     * @return: A list of string
     */
    public List wordSearchII(char[][] board, List words) {
        // write your code here
        Node root = new Node("");
//        构造一个树来存储整个字典
        for (String word : words) {
            root.insert(word);
        }
        ArrayList res = new ArrayList<>();
        for (int i = 0; i < board.length; i++) {
            for (int j = 0; j < board[0].length; j++) {
                tree(i, j, "", root, board, res);
            }
        }
        return res;
    }

    private void tree(int i, int j, String s, Node root, char[][] board, List res) {
        if (i >= 0 && i < board.length && j >= 0 && j < board[0].length) {
            s += board[i][j];
            int temp = root.find(s);
            if (temp == 2) {
//                如果找到单词就加入
                if (!res.contains(s)) {
                    res.add(s);
                }
            }
//            只要找到节点,下个字符串就有可能在字典中,
            if (temp >= 1) {
                char c = board[i][j];
                board[i][j] = '#';
//                修改当前的值,防止重复使用
                tree(i + 1, j, s, root, board, res);
                tree(i - 1, j, s, root, board, res);
                tree(i, j - 1, s, root, board, res);
                tree(i, j + 1, s, root, board, res);
//                还需要修改回来
                board[i][j] = c;
            }
        }
    }

    private class Node {
        //表示当前的字符串
        String lab;
        //如果有单词,它一定lab相同
        String word;
        //子节点比当前的lab多一个字母
        List nodes = new ArrayList<>();

        public Node(String lab) {
            this.lab = lab;
        }

        public void insert(String word) {
            if (lab.equals(word)) {
//                如果当前lab和要插入的单词相同,就对word进行赋值然后返回
                this.word = word;
                return;
            }
            int len = lab.length();
            String pre = word.substring(0, len + 1);
//            取比lab多一个字母
            for (int i = 0; i < nodes.size(); i++) {
                Node node = nodes.get(i);
//                去子节点中查找,如果找到就递归,
                if (node.lab.equals(pre)) {
                    node.insert(word);
                    return;
                }
            }
//            找不到就新建一个节点
            Node node = new Node(pre);
            nodes.add(node);
            node.insert(word);
        }

        /**
         * 0表示完全没有,1表示找到这个节点了但是没有这个单词,2表示有这个单词
         *
         * @param s
         * @return
         */
        public int find(String s) {
//            找到这个节点
            if (s.equals(lab)) {
                if (s.equals(word)) {
//                    找到了单词,
                    return 2;
                } else {
//                    找到了节点,
                    return 1;
                }
            }
            if (s.startsWith(lab)) {
//                递归查找它的子节点
                for (int i = 0; i < nodes.size(); i++) {
                    Node node = nodes.get(i);
                    int i1 = node.find(s);
                    if (i1 != 0) {
                        return i1;
                    }
                }
            }
            return 0;
        }
    }
}

你可能感兴趣的:(Word Search II)