这是我参与11月更文挑战的第7天,活动详情查看:2021最后一次更文挑战
题五
实现 Trie (前缀树)
Trie(发音类似 "try")或者说 前缀树 是一种树形数据结构,用于高效地存储和检索字符串数据集中的键。这一数据结构有相当多的应用情景,例如自动补完和拼写检查。
请你实现 Trie 类:
Trie() 初始化前缀树对象。 void insert(String word) 向前缀树中插入字符串 word 。
boolean search(String word) 如果字符串 word 在前缀树中,返回 true(即,在检索之前已经插入);否则,返回 false 。
boolean startsWith(String prefix) 如果之前已经插入的字符串 word 的前缀之一为 prefix ,返回 true ;否则,返回 false 。
示例:
输入 ["Trie", "insert", "search", "search", "startsWith", "insert", "search"] [[], ["apple"], ["apple"], ["app"], ["app"], ["app"], ["app"]] 输出 [null, null, true, false, true, null, true]
解释
Trie trie = new Trie();
trie.insert("apple");
trie.search("apple"); // 返回 True
trie.search("app"); // 返回 False
trie.startsWith("app"); // 返回 True
trie.insert("app");
trie.search("app"); // 返回 True
提示:
1 <= word.length, prefix.length <= 2000
word 和 prefix 仅由小写英文字母组成
insert、search 和 startsWith 调用次数 总计 不超过 3 * 104 次
相关标签
- 设计
- 字典树
- 哈希表
- 字符串
解题思路:
- 前缀树 == 字典树
- 构建一个节点,节点递归下一个节点
代码:
from collections import defaultdict
class TrieNode:
def __init__(self):
self.child = defaultdict(TrieNode)
self.word = False
class Trie:
def __init__(self):
'''
初始化
'''
self.root = TrieNode()
def insert(self, word):
'''
实现insert功能
'''
cur = self.root
for s in word:
cur = cur.child[s]
cur.word = True
def search(self, word):
'''
实现search功能
'''
cur = self.root
for l in word:
if l not in cur.child:
return False
cur = cur.child[l]
if cur.word :
return True
return False
def startsWith(self, prefix):
'''
实现startsWith 功能
'''
cur = self.root
for p in prefix:
if p not in cur.child:
return False
cur = cur.child[p]
return True
# Your Trie object will be instantiated and called as such:
# obj = Trie()
# obj.insert(word)
# param_2 = obj.search(word)
# param_3 = obj.startsWith(prefix)
执行结果:
题六:
单词搜索 II
给定一个 m x n 二维字符网格 board 和一个单词(字符串)列表 words,找出所有同时在二维网格和字典中出现的单词。
单词必须按照字母顺序,通过 相邻的单元格 内的字母构成,其中“相邻”单元格是那些水平相邻或垂直相邻的单元格。同一个单元格内的字母在一个单词中不允许被重复使用。
示例 1:
输入:board = [["o","a","a","n"],["e","t","a","e"],["i","h","k","r"],["i","f","l","v"]], words = ["oath","pea","eat","rain"]
输出:["eat","oath"]
示例 2:
输入:board = [["a","b"],["c","d"]], words = ["abcb"]
输出:[] 提示:
m == board.length
n == board[i].length
1 <= m, n <= 12
board[i][j] 是一个小写英文字母
1 <= words.length <= 3 * 104
1 <= words[i].length <= 10
words[i] 由小写英文字母组成
words 中的所有字符串互不相同
相关标签
- 字典树
- 数组
- 字符串
- 回溯
- 矩阵
利用上一题的字典树 算法 再加上dfs 回溯的算法实现此题
from collections import defaultdict
class Trie:
def __init__(self):
self.child = defaultdict(Trie)
self.val = ""
self.words = ""
def insert(self, word):
cur = self
for c in word:
cur = cur.child[c]
cur.val = c
cur.words = word
class Solution:
def findWords(self, board: List[List[str]], words: List[str]) -> List[str]:
def dfs(i, j, node):
word = board[i][j]
node = node.child[word]
if word != node.val:
return
if node.words != "":
res.add(node.words)
board[i][j] = "accessed"
for l1,l2 in [(i-1, j), (i+1, j), (i, j-1), (i, j+1)]:
if 0 <= l1 <= n-1 and 0 <= l2 <= m-1:
t = board[l1][l2]
if t != "accessed":
dfs(l1, l2, node)
board[i][j] = word
n = len(board)
m = len(board[0])
res = set()
trie = Trie()
for word in words:
trie.insert(word)
for i in range(n):
for j in range(m):
dfs(i,j, trie)
return list(res)
运行结果:
虽然效率有点低,但是算是做出来了,再查一查资料,看一下有没有更优的解题思路或者方法