Giả sử chúng ta phải thiết kế một cấu trúc dữ liệu hỗ trợ hai hoạt động sau -
-
addWord (từ)
-
tìm kiếm (từ)
Phương thức search (word) có thể tìm kiếm một từ theo nghĩa đen hoặc một chuỗi biểu thức chính quy chỉ chứa các chữ cái a-z hoặc .. A. có nghĩa là nó có thể đại diện cho bất kỳ một chữ cái nào. Vì vậy, ví dụ:nếu chúng tôi thêm một số từ như "tệ", "cha", "điên", sau đó tìm kiếm tìm kiếm ("pad") → sai, tìm kiếm ("xấu") → đúng, tìm kiếm (". Ad") → true và tìm kiếm (“b ..”) → true
Để giải quyết vấn đề này, chúng tôi sẽ làm theo các bước sau -
-
Có một số phương thức, ban đầu hãy xác định insertNode (), điều này sẽ lấy tham chiếu head và chuỗi s, điều này sẽ hoạt động như sau -
-
curr:=head, n:=size of s
-
cho tôi trong phạm vi từ 0 đến n - 1
-
x:=s [i]
-
nếu con [x] của curr không phải là null, thì con [x] của curr:=nút mới
-
curr:=child [x] of curr
-
-
đặt isEnd of curr là true
-
Từ addWord (), gọi phương thức insertNode () này
-
Định nghĩa một phương thức khác được gọi là check (), phương thức này sẽ nhận curr, string s và index. Ban đầu chỉ mục là 0. Điều này sẽ hoạt động như sau -
-
nếu index =size of s, thì trả về isEnd of curr
-
đặt ok:=true
-
nếu s [index] là dấu chấm thì
-
cho tôi trong phạm vi từ 0 đến 25
-
x:=ASCII của ‘a’ + i
-
nếu con [x] của curr AND kiểm tra (con [x] của curr, s, index + 1) là đúng, thì trả về true.
-
-
-
nếu không thì
-
x:=s [chỉ số]
-
nếu con [x] của curr AND kiểm tra (con [x] của curr, s, index + 1) là đúng, thì trả về true.
-
-
trả về false
-
Từ phương pháp tìm kiếm, đặt curr:=head và return check (curr, word, 0)
Ví dụ (C ++)
Hãy cùng chúng tôi xem cách triển khai sau để hiểu rõ hơn -
#include <bits/stdc++.h>
using namespace std;
struct Node{
bool isEnd;
map <char, Node*> child;
Node(){
isEnd = false;
}
};
class WordDictionary {
public:
Node* head;
WordDictionary() {
head = new Node();
}
void insertNode(Node* head, string s){
Node* curr = head;
int n = s.size();
for(int i = 0; i < n; i++){
char x = s[i];
if(!curr->child[x]){
curr->child[x] = new Node();
}
curr = curr->child[x];
}
curr->isEnd = true;
}
void addWord(string word) {
insertNode(head, word);
}
bool check(Node* curr, string s, int idx = 0){
if(idx == s.size()) return curr->isEnd;
bool ok = false;
if(s[idx] == '.'){
for(int i = 0; i < 26; i++){
char x = 'a' + i;
if(curr->child[x] && check(curr->child[x], s, idx + 1))return true;
}
} else {
char x = s[idx];
if(curr->child[x] && check(curr->child[x], s, idx + 1))return true;
}
return false;
}
bool search(string word) {
Node* curr = head;
return check(curr, word);
}
};
main(){
WordDictionary ob;
ob.addWord("bad");
ob.addWord("dad");
ob.addWord("mad");
cout << (ob.search("pad")) << endl;
cout << (ob.search("bad")) << endl;
cout << (ob.search(".ad")) << endl;
cout << (ob.search("b..")) << endl;
} Đầu vào
Initialize the WordDictionary, then call the addWord() methods ans search methods. See in the main() function
Đầu ra
0 1 1 1