[LeetCode] Concatenated Words 连接的单词
Given a list of words (without duplicates), please write a program that returns all concatenated words in the given list of words.
A concatenated word is defined as a string that is comprised entirely of at least two shorter words in the given array.
Example:
Input: ["cat","cats","catsdogcats","dog","dogcatsdog","hippopotamuses","rat","ratcatdogcat"] Output: ["catsdogcats","dogcatsdog","ratcatdogcat"] Explanation: "catsdogcats" can be concatenated by "cats", "dog" and "cats";
"dogcatsdog" can be concatenated by "dog", "cats" and "dog";
"ratcatdogcat" can be concatenated by "rat", "cat", "dog" and "cat".
Note:
- The number of elements of the given array will not exceed
10,000 - The length sum of elements in the given array will not exceed
600,000. - All the input string will only include lower case letters.
- The returned elements order does not matter.
这道题给了一个由单词组成的数组,某些单词是可能由其他的单词组成的,让我们找出所有这样的单词。这道题跟之前那道Word Break十分类似,我们可以对每一个单词都调用之前那题的方法,我们首先把所有单词都放到一个unordered_set中,这样可以快速找到某个单词是否在数组中存在。对于当前要判断的单词,我们先将其从set中删去,然后调用之前的Word Break的解法,具体讲解可以参见之前的帖子。如果是可以拆分,那么我们就存入结果res中,参见代码如下:
解法一:
class Solution {
public:
vector<string> findAllConcatenatedWordsInADict(vector<string>& words) {
if (words.size() <= ) return {};
vector<string> res;
unordered_set<string> dict(words.begin(), words.end());
for (string word : words) {
dict.erase(word);
int len = word.size();
if (len == ) continue;
vector<bool> v(len + , false);
v[] = true;
for (int i = ; i < len + ; ++i) {
for (int j = ; j < i; ++j) {
if (v[j] && dict.count(word.substr(j, i - j))) {
v[i] = true;
break;
}
}
}
if (v.back()) res.push_back(word);
dict.insert(word);
}
return res;
}
};
下面这种方法跟上面的方法很类似,不同的是判断每个单词的时候不用将其移除set,而是在判断的过程中加了判断,使其不会判断单词本身是否在集合set中存在,而且由于对单词中子字符串的遍历顺序不同,加了一些优化在里面,使得其运算速度更快一些,参见代码如下:
解法二:
class Solution {
public:
vector<string> findAllConcatenatedWordsInADict(vector<string>& words) {
vector<string> res;
unordered_set<string> dict(words.begin(), words.end());
for (string word : words) {
int n = word.size();
if (n == ) continue;
vector<bool> dp(n + , false);
dp[] = true;
for (int i = ; i < n; ++i) {
if (!dp[i]) continue;
for (int j = i + ; j <= n; ++j) {
if (j - i < n && dict.count(word.substr(i, j - i))) {
dp[j] = true;
}
}
if (dp[n]) {res.push_back(word); break;}
}
}
return res;
}
};
下面这种方法是递归的写法,其中递归函数中的cnt表示有其他单词组成的个数,至少得由其他两个单词组成才符合题意,参见代码如下:
解法三:
class Solution {
public:
vector<string> findAllConcatenatedWordsInADict(vector<string>& words) {
vector<string> res;
unordered_set<string> dict(words.begin(), words.end());
for (string word : words) {
if (word.empty()) continue;
if (helper(word, dict, , )) {
res.push_back(word);
}
}
return res;
}
bool helper(string& word, unordered_set<string>& dict, int pos, int cnt) {
if (pos >= word.size() && cnt >= ) return true;
for (int i = ; i <= (int)word.size() - pos; ++i) {
string t = word.substr(pos, i);
if (dict.count(t) && helper(word, dict, pos + i, cnt + )) {
return true;
}
}
return false;
}
};
类似题目:
参考资料:
https://discuss.leetcode.com/topic/72393/c-772-ms-dp-solution
LeetCode All in One 题目讲解汇总(持续更新中...)
[LeetCode] Concatenated Words 连接的单词的更多相关文章
- 472 Concatenated Words 连接的单词
详见:https://leetcode.com/problems/concatenated-words/description/ C++: class Solution { public: vecto ...
- [LeetCode] Valid Word Square 验证单词平方
Given a sequence of words, check whether it forms a valid word square. A sequence of words forms a v ...
- [LeetCode] Valid Word Abbreviation 验证单词缩写
Given a non-empty string s and an abbreviation abbr, return whether the string matches with the give ...
- [LeetCode] Shortest Word Distance 最短单词距离
Given a list of words and two words word1 and word2, return the shortest distance between these two ...
- [LeetCode] Short Encoding of Words 单词集的短编码
Given a list of words, we may encode it by writing a reference string S and a list of indexes A. For ...
- [LeetCode] Expressive Words 富于表现力的单词
Sometimes people repeat letters to represent extra feeling, such as "hello" -> "he ...
- LeetCode 79 Word Search(单词查找)
题目链接:https://leetcode.com/problems/word-search/#/description 给出一个二维字符表,并给出一个String类型的单词,查找该单词是否出现在该二 ...
- LeetCode 290 Word Pattern(单词模式)(istringstream、vector、map)(*)
翻译 给定一个模式,和一个字符串str.返回str是否符合同样的模式. 这里的符合意味着全然的匹配,所以这是一个一对多的映射,在pattern中是一个字母.在str中是一个为空的单词. 比如: pat ...
- LeetCode 1255 得分最高的单词集合 Maximum Score Words Formed by Letters
地址 https://leetcode-cn.com/problems/maximum-score-words-formed-by-letters/ 题目描述你将会得到一份单词表 words,一个字母 ...
随机推荐
- Cesium原理篇:Material
Shader 首先,在本文开始前,我们先普及一下材质的概念,这里推荐材质,普及材质的内容都是截取自该网站,我觉得他写的已经够好了.在开始普及概念前,推荐一首我此刻想到的歌<光---陈粒>. ...
- SQL Server 统计信息更新时采样百分比对数据预估准确性的影响
为什么要写统计信息 最近看到园子里有人写统计信息,楼主也来凑热闹. 话说经常做数据库的,尤其是做开发的或者优化的,统计信息造成的性能问题应该说是司空见惯. 当然解决办法也并非一成不变,“一招鲜吃遍天” ...
- 你真的会玩SQL吗?冷落的Top和Apply
你真的会玩SQL吗?系列目录 你真的会玩SQL吗?之逻辑查询处理阶段 你真的会玩SQL吗?和平大使 内连接.外连接 你真的会玩SQL吗?三范式.数据完整性 你真的会玩SQL吗?查询指定节点及其所有父节 ...
- 重定向Http status code 303 和 302
http 302 http 303 Http 302 302是一个普通的重定向代码.直观的看来是,请求者(浏览器或者模拟http请求)发起一个请求,然后服务端重定向到另一个地址.而事实上,服务端仅仅是 ...
- Python中的类、对象、继承
类 Python中,类的命名使用帕斯卡命名方式,即首字母大写. Python中定义类的方式如下: class 类名([父类名[,父类名[,...]]]): pass 省略父类名表示该类直接继承自obj ...
- AngularJS中get请求URL出现跨域问题
今天早上帮助同学看了一个AngularJS的问题,主要是请求中出现了跨域访问,请求被阻止. 下面是她给我的代码: <html lang="en" ng-app="m ...
- 【手记】调用Process.EnterDebugMode引发异常:并非所有引用的特权或组都分配给呼叫方
刚上线一个新版本,其中有台电脑打开软件就报[xx的类型初始值设定项引发异常](还好不是一大波电脑,新东西上线就怕哀鸿遍野),如图: 显然是该类型的静态构造函数中抛异常了(红线处就是类名),遂打开该类, ...
- Java中的多线程你只要看这一篇就够了
学习Java的同学注意了!!! 学习过程中遇到什么问题或者想获取学习资源的话,欢迎加入Java学习交流群,群号码:279558494 我们一起学Java! 引 如果对什么是线程.什么是进程仍存有疑惑, ...
- Android 手机卫士8--删除通话记录
1.编写代码需要注意bug: 再删除通话记录的时候,删除的是以前的通话记录,本次拦截下来的电话号码,通话记录没有删除?????? 问题原因:数据库中本次通话记录的电话号码还没有插入,就做了删除操作 2 ...
- linux(十二)___Apache服务器用户认证、虚拟主机的配置
创建xiangkejin zhangsan两个用户 可看见文件中创建的两个用户: 建立虚拟目录并配置用户认证 ①建立虚拟目录 /xiangkejin ②在Apache的主配置文件httpd.conf ...