这道题目实际上可以用到之前的leetcode139中的算法word break
我们先对words数组排序,排序的目的是减少后续的比较
核心思路:每次循环里面直接判断当前的words[i]是不是可以由字典里面的数字组成(word break算法)。
注意我们写代码的顺序,要等每次判断某个words[i]是否可以拆分 再把这个字符加入到字典里面。
class Solution {
public static List<String> findAllConcatenatedWordsInADict(String[] words) {
List<String> result = new ArrayList<>();
Set<String> preWords = new HashSet<>();
Arrays.sort(words, new Comparator<String>() {
@Override
public int compare(String o1, String o2) {
return o1.length()-o2.length();
}
});
for (int i = 0; i < words.length; i++) {
if (wordBreak(words[i], preWords)) {
result.add(words[i]);
}
preWords.add(words[i]);//记得要判断后再添加,不然自己就会被加入result
}
return result;
}
public static boolean wordBreak(String s, Set<String> hashset) {
if(hashset.isEmpty())return false;
int n = s.length();
boolean []dp = new boolean[n+1];
dp[0]=true;
for(int i=1;i<=n;i++){
for(int j=i;j>=0;j--){
if(!dp[j]) continue;
String substring = s.substring(j,i);
if(hashset.contains(substring)){
if(dp[j]){
dp[i]=true;
break;
}
}
}
}
return dp[n];
}
}