Problem description
Given a non-empty string s and a dictionary word Dict containing a list of non-empty words, it is determined whether s can be split into one or more words in the dictionary by spaces.
Explain:
The words in the dictionary can be reused when splitting.
You can assume that there are no repetitive words in the dictionary.
Example 1:
Input: s = leetcode, wordDict = ["leet", "code"]
Output: true
Interpretation: Return true because "leet code" can be split into "leet code".
Example 2:
Input: s = applepenapple, wordDict = ["apple", "pen"]
Output: true
Interpretation: Return true because "apple pen apple" can be split into "apple pen apple".
Note that you can reuse the words in the dictionary.
Example 3:
Input: s = catsandog, wordDict = ["cats", "dog", "sand", "and", "cat"]
Output: false
Solving problems
code implementation
package solution; import java.util.*; class Solution { List<List<String>> lists; public static void main(String[] args) { List<String> list=new ArrayList<>(); list.add("cats"); list.add("dog"); list.add("sand"); list.add("and"); list.add("cat"); new Solution().wordBreak("catsandog",list); } public boolean wordBreak(String s, List<String> wordDict) { if (s == null || s.length() == 0) { return true; } Set<String> set = new HashSet<>(wordDict); int maxLen = getMaxLen(set); // A word of length n has a total of n + 1 tangent points boolean[] canSegment = new boolean[s.length() + 1]; canSegment[0] = true; for (int i = 1; i < canSegment.length; i ++) { for (int j = 1; j <= maxLen && j <= i; j ++) { // i - j denotes j positions from i to forward String str = s.substring(i - j, i); //If the word qualifies and the first letter of the word corresponds to the canSegment, it is already true. if (set.contains(str) && canSegment[i - j]) { canSegment[i] = true; break; } } } return canSegment[canSegment.length - 1]; } private int getMaxLen(Set<String> set) { int maxLen = 0; for (String word : set) { maxLen = Math.max(maxLen, word.length()); } return maxLen; } }
Word splitting 2
Given a non-empty string s and a dictionary word Dict containing a list of non-empty words, add spaces to the string to construct a sentence so that all the words in the sentence are in the dictionary. Return all these possible sentences.
Explain:
The words in the dictionary can be reused when separating.
You can assume that there are no repetitive words in the dictionary.
Example 1:
input: s = "catsanddog" wordDict = ["cat", "cats", "and", "sand", "dog"] //Output: [ "cats and dog", "cat sand dog" ]
Example 2:
Input: s = "pineapplepenapple" wordDict = ["apple", "pen", "applepen", "pine", "pineapple"] Output: [ "pine apple pen apple", "pineapple pen apple", "pine applepen apple" ] Explanation: Note that you can reuse the words in the dictionary.
Example 3:
input: s = "catsandog" wordDict = ["cats", "dog", "sand", "and", "cat"] //Output: []
package solution; import java.util.ArrayList; import java.util.List; public class Solution4 { public static void main(String[] args) { String s="catsanddog"; List<String> wordDict = new ArrayList<>(); wordDict.add("cat"); wordDict.add("cats"); wordDict.add("dog"); wordDict.add("sand"); wordDict.add("and"); new Solution4().wordBreak(s,wordDict); System.out.println(s); } private List<String> result; public List<String> wordBreak(String s, List<String> wordDict) { if (wordDict.size()<1){ return new ArrayList<>(); } result=new ArrayList<>(); //Judge first whether it can be split if(!confirm(s,wordDict)){ return result; } //Each traversal of split markup boolean[] flag=new boolean[s.length()]; //If it can be split find(s,0,flag,wordDict); return result; } private boolean confirm(String s,List<String> words){ boolean[] flag=new boolean[s.length()+1]; flag[0]=true; //Find the longest word length in the dictionary int maxLen=findMax(words); for(int i=1;i<flag.length;i++){ //To see if the words before i are satisfied, the maximum length of the word is maxLen for(int j=1;j<=maxLen&&j<=i;j++) { String str=s.substring(i-j,i); //The first letter of str corresponds to a mark that is true, and str is in the dictionary. if(flag[i-j]&&words.contains(str)){ flag[i]=true; } } } return flag[flag.length-1]; } private int findMax(List<String> words) { int max=words.get(0).length(); for(String s:words){ if(max<s.length()){ max=s.length(); } } return max; } private void find(String s,int index,boolean[] flag,List<String> words){ //After marking up, the segmentation begins. if(index==s.length()){ StringBuilder sb=new StringBuilder(); int begin=0;//Segmentation starting point for(int last=0;last<s.length();last++){ if(flag[last]){ sb.append(s.substring(begin,last+1)+" "); begin=last+1; } } sb.deleteCharAt(sb.length()-1); result.add(sb.toString()); } for(int i=index;i<s.length();i++){ //Mark qualified words from index if(words.contains(s.substring(index,i+1))){ flag[i]=true; //Satisfies the condition, then marks from i+1 find(s,i+1,flag,words); //After a round of traversal, all markers are cleared flag[i]=false; } } } }