这道题就是320和408两个题目合在一起:

 

唯一需要注意的是,需要返回最短的长度,而最短的长度中数字只算一个长度,例如  the abbreviation "a32bc" has length = 4, 因为“32”长度算1.

因此定义一个class node, 不仅存放abbreviation 也存放  定义的“长度”,并且在dfs 中容易算出这个长度, 比如dfs 中 遇到 "10" 只需要长度 +1 即可。

code 长的有点恶心了,就是把 320 和 408 的code 合并在了一起而已。

class Solution {
    public String minAbbreviation(String target, String[] dictionary) {
        //"usaandchinaarefriends" [] 过这个case
        if(dictionary == null || dictionary.length ==0) return target.length()+"";
        
        List<String> dic = new ArrayList<>();
        for(String str: dictionary){  //去掉字典里和 target 里长度不同的单词
            if(str.length() == target.length()){
                dic.add(str);
            }
        }
        
        List<Node> result = new ArrayList<>();
        dfs(new StringBuilder(), result, target,0,0);
        
        Collections.sort(result,(o1,o2)->o1.len-o2.len);
       
        //int min_len = Integer.MAX_VALUE;
        //String min_str = "";
        for(Node node: result){
           boolean flag = false;
           for(String word: dic) {
               //System.out.println(node.abbr);
               flag = validWordAbbreviation(word,node.abbr);
               if(flag) break;
           }
           if(!flag){
               return node.abbr;
           }
         
        }
        
        return "";
    }
    
    private void dfs(StringBuilder curResult,List<Node> result, String word, int cur_index,int abbr_len){
        if(curResult.length() == word.length() || cur_index == word.length()){
            result.add(new Node(curResult.toString(), abbr_len));
            return;
        }
       
        int len = curResult.length(); // 每次记录长度
       

        //put the 剩下的可能的长度
        for(int i=1; i<=word.length()-cur_index; i++){ // wrd: cur_index = 0, len =3, 可以放 1,2,3
            // 当前result 里 最后一个字符得是字母才能 放数字
            if(curResult.length()==0 || Character.isLetter(curResult.charAt(curResult.length()-1)) ){
                curResult.append(i);
                dfs(curResult,result,word,cur_index+i,abbr_len+1);
                curResult.setLength(len); //恢复之前的长度
            }   
        }
        
      // put cur letter
        curResult.append(word.charAt(cur_index));
        dfs(curResult,result, word,cur_index+1,abbr_len+1);
        curResult.setLength(len);
    }
    
    private boolean validWordAbbreviation(String word, String abbr) {
        int index = 0;
        String count = "0";
        for(int i=0; i<abbr.length(); i++){
            char c = abbr.charAt(i);  
            if(Character.isLetter(c) ) {
                index = index + Integer.valueOf(count);
                if(index >= word.length() || c != word.charAt(index) ) return false;
                count = "0";
                index++;
            }  
            else {
                if(count.equals("0") && c=='0') return false;
                count += c;
               
            }
        }
    
        return index + Integer.valueOf(count) == word.length();
    }
}

class Node{
    String abbr;
    int len ;
    Node(String abbr, int len){
        this.abbr = abbr;
        this.len = len;
    }
}

 

posted on 2018-11-12 15:39  KeepAC  阅读(137)  评论(0编辑  收藏  举报