zoukankan      html  css  js  c++  java
  • leetcode616- Add Bold Tag in String- medium

    Given a string s and a list of strings dict, you need to add a closed pair of bold tag <b> and </b> to wrap the substrings in s that exist in dict. If two such substrings overlap, you need to wrap them together by only one pair of closed bold tag. Also, if two substrings wrapped by bold tags are consecutive, you need to combine them.

    Example 1:

    Input: 
    s = "abcxyz123"
    dict = ["abc","123"]
    Output:
    "<b>abc</b>xyz<b>123</b>"
    

    Example 2:

    Input: 
    s = "aaabbcc"
    dict = ["aaa","aab","bc"]
    Output:
    "<b>aaabbc</b>c"
    

    Note:

    1. The given dict won't contain duplicates, and its length won't exceed 100.
    2. All the strings in input have length in range [1, 1000].

    算法:关键是找需不需要加bold这个事情怎么尽量降低复杂度。这种问题一般输入的字符串(L)可能很长很长的,但字典大小(k)一般是有限制的,所以尽量避免对字符串i,j限制找是不是符合条件,因为这样复杂度直接L^3了(双重循环+contains查)。而是可以换成for循环一次指着字符串开头,然后for循环所有词典来查看接下来的单词是不是以词典单词为前缀的 s.startsWith(word, i);,这样时间复杂度是O(L^2 * K)。这样在字符串输入可以无限长的情况下就降一个维度了,很可以。

    具体处理:

    法1.用一个boolean[] isBold数组一开始这样标记好某个位置要不要加粗,后续进行加粗处理。

    法2.用Interval。一开始加入加粗区间,然后做一个mergeInterval,然后根据最后的intervals拼字符串。拼法最好是先用原来的,然后之后stringBuilder.insert(index, string); 而且注意每次加了以后后续再加标记都要再多一点offset。

    实现1:

    public class Solution {
        public String addBoldTag(String s, String[] dict) {
            boolean[] bold = new boolean[s.length()];
            for (int i = 0, end = 0; i < s.length(); i++) {
                for (String word : dict) {
                    if (s.startsWith(word, i)) {
                        end = Math.max(end, i + word.length());
                    }
                }
                bold[i] = end > i;
            }
            
            StringBuilder result = new StringBuilder();
            for (int i = 0; i < s.length(); i++) {
                if (!bold[i]) {
                    result.append(s.charAt(i));
                    continue;
                }
                int j = i;
                while (j < s.length() && bold[j]) j++;
                result.append("<b>" + s.substring(i, j) + "</b>");
                i = j - 1;
            }
            
            return result.toString();
        }
    }

    实现2:

    class Solution {
        private class Interval{
            public int start;
            public int end;
            public Interval(int start, int end) {
                this.start = start;
                this.end = end;
            }
        }
    
        public String addBoldTag(String s, String[] dict) {
            if (s == null || s.length() == 0 || dict == null || dict.length == 0) {
                return s;
            }
            Set<String> set = new HashSet<>();
            int maxL = Integer.MIN_VALUE;
            for (int i = 0; i < dict.length; i++) {
                set.add(dict[i]);
                maxL = Math.max(maxL, dict[i].length());
            }
            List<Interval> intervals = new ArrayList<>();
            for (int i = 0; i < s.length(); i++) {
                for (String word : dict) {
                    if (s.startsWith(word, i)) {
                        intervals.add(new Interval(i, i + word.length() - 1));
                    }
                }
                // 时间复杂度太高了
                // for (int j = i; j <= s.length() && j <= i + maxL + 1; j++) {
                //     if (set.contains(s.substring(i, j))) {
                //         intervals.add(new Interval(i, j - 1));
                //     }
                // }
            }
    
            if (intervals.size() == 0) {
                return s;
            }
            intervals = mergeIntervals(intervals);
    
            int offset = 0;
            StringBuilder sb = new StringBuilder(s);
            for (int i = 0; i < intervals.size(); i++) {
                // 注意insert这种操作
                sb.insert(intervals.get(i).start + offset, "<b>");
                offset += 3;
                sb.insert(intervals.get(i).end + 1 + offset, "</b>");
                offset += 4;
            }
    
            return sb.toString();
        }
    
        private List<Interval> mergeIntervals(List<Interval> intervals) {
            List<Interval> result = new ArrayList<>();
            Interval prev = intervals.get(0);
            Interval crt;
            for (int i = 1; i < intervals.size(); i++) {
                crt = intervals.get(i);
                if (crt.start <= prev.end + 1) {
                    prev.end = Math.max(prev.end, crt.end);
                } else {
                    result.add(prev);
                    prev = crt;
                }
            }
            result.add(prev);
            return result;
        }
    }
  • 相关阅读:
    *pwn*练习1——攻防世界-when_did_you_born
    PWN——uaf漏洞学习
    pwnable.kr之passcode
    pwnable.kr之flag
    pwnable.kr之brainf*ck
    pwnable.kr之simple Login
    pwnable.tw start&orw
    RTF文件格式
    jarvis level6_x64堆溢出unlink拾遗
    jarvisoj level5爬坑
  • 原文地址:https://www.cnblogs.com/jasminemzy/p/7975221.html
Copyright © 2011-2022 走看看