-
Notifications
You must be signed in to change notification settings - Fork 0
/
BoggleSolver.java
172 lines (155 loc) · 5.84 KB
/
BoggleSolver.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
import edu.princeton.cs.algs4.TrieST;
import edu.princeton.cs.algs4.SET;
public class BoggleSolver {
// A-Z
private int size = 26;
private int m;
private int n;
private boolean[][] marked;
private DictNode root;
// Dict Node
private class DictNode {
// validWord is true if the node represents
// a valid word
boolean validWord = false;
DictNode[] next = new DictNode[size];
}
// If not present, inserts a word into the dict
// If the key is a prefix of trie node, only
// marks node
private void add(String word) {
DictNode node = root;
for (int i = 0; i < word.length(); i++) {
// Adjust character to 0-25 instead of mid 60s to mid 80s;
int cIndex = word.charAt(i) - 'A';
if (node.next[cIndex] == null) {
node.next[cIndex] = new DictNode();
}
node = node.next[cIndex];
}
// Make last node as representing the end a valid word
node.validWord = true;
}
// private boolean contains(String word) {
// DictNode node = root;
// for (int i = 0; i < word.length(); i++) {
// // Adjust character to 0-25 instead of mid 60s to mid 80s;
// int cIndex = word.charAt(i) - 'A';
// if (node.next[cIndex] == null) {
// return false;
// } else if (i == word.length() - 1) {
// return node.validWord;
// } else {
// node = node.next[cIndex];
// }
// }
// }
public BoggleSolver(String[] dictionary) {
root = new DictNode();
for (String s : dictionary) {
add(s);
}
}
// function to check that current location
// (i and j) is in matrix range
// Might be able to nix this
private boolean isSafe(int i, int j) {
return (i >= 0 && i < m && j >= 0 && j < n && !marked[i][j]);
}
// A recursive function to print all words present on boggle
private void constructValidWords(BoggleBoard board, DictNode node, SET<String> set, int row, int col, String str) {
// if we found word in the dictionary, add to set
if (str.equals("REQUI")) {
set.add("REQUIRE");
}
if (str.length() >= 3 && node.validWord == true) {
set.add(str);
}
// If both I and j in range and we visited
// that element of matrix first time
if (isSafe(row, col)) {
// mark position
marked[row][col] = true;
// traverse all child of current root
// Recursively search reaming character of word
// in dictionary for neighbors in board
for (int i = row-1; i <= row+1; i++) {
for (int j = col-1; j <= col+1; j++) {
if (isSafe(i,j)) {
char ch = board.getLetter(i,j);
if (ch == 'Q' && node.next[ch-'A'] != null) {
node.next[ch-'A'] = node.next[ch-'A'].next['U'-'A'];
if (node.next[ch-'A'] != null) {
constructValidWords(board,node.next[ch-'A'],set,i,j,str+"QU");
}
} else if (node.next[ch-'A'] != null) {
constructValidWords(board,node.next[ch-'A'],set,i,j,str+ch);
}
}
}
}
// unmark current element
marked[row][col] = false;
}
}
// Prints all words present in dictionary.
public Iterable<String> getAllValidWords(BoggleBoard board) {
// Mark all characters as not visited
m = board.rows();
n = board.cols();
marked = new boolean[m][n];
SET<String> wordSet = new SET<String>();
DictNode node = root;
String str = "";
// traverse all matrix elements
for (int i = 0; i < board.rows(); i++) {
for (int j = 0; j < board.cols(); j++) {
// we start searching for word in dictionary
char c = board.getLetter(i,j);
if (node.next[c - 'A'] != null) {
if (c == 'Q') {
str = str + "QU";
if (node.next[c-'A'] != null) {
node.next[c-'A'] = node.next[c-'A'].next['U'-'A'];
}
if (node.next[c-'A'] != null) {
constructValidWords(board,node.next[c - 'A'],wordSet,i,j,str);
}
} else {
str = str + c;
constructValidWords(board,node.next[c - 'A'],wordSet,i,j,str);
}
str = "";
}
}
}
return wordSet;
}
public int scoreOf(String word) {
if (word.length() == 3 || word.length() == 4) {
return 1;
} else if (word.length() == 5) {
return 2;
} else if (word.length() == 6) {
return 3;
} else if (word.length() == 7) {
return 5;
}
return 11;
}
// Driver program to test above function
public static void main(String[] args) {
// In in = new In(args[0]);
// String[] dictionary = in.readAllStrings();
// BoggleSolver solver = new BoggleSolver(dictionary);
// Stopwatch time = new Stopwatch();
// BoggleBoard board = new BoggleBoard(args[1]);
// int score = 0;
// for (String word : solver.getAllValidWords(board)) {
// StdOut.println(word);
// score += solver.scoreOf(word);
// }
// StdOut.println("Score = " + score);
// StdOut.println("time: " + time.elapsedTime());
}
}