LintCode 1819: Longest Semi Alternating Substring

1819. Longest Semi Alternating Substring

You are given a string SS of length NN containing only characters a and b. A substring (contiguous fragment) of SS is called a semi-alternating substring if it does not contain three identical consecutive characters. In other words, it does not contain either aaa or bbb substrings. Note that whole SS is its own substring.

Write a function, which given a string SS, returns the length of the longest semi-alternating substring of SS.

Example

Example 1

Input: "baaabbabbb"
Output: 7
Explanation: "aabbabb" is the longest semi-alternating substring.

Example 2

Input: "babba"
Output: 5
Explanation: Whole S is semi-alternating.

Example 3

Input: "abaaaa"
Output: 4
Explanation: "abaa" is the longest semi-alternating substring.

Notice

  • NN is an integer within the range [1,200\,000][1,200000];
  • string SS consists only of the characters a and/or b.

Input test data (one parameter per line)How to understand a testcase?

解法1:我的思路就是把"baaabbabbb"先转换成13213这样的int数组,然后再扫描这个int数组,如果其值<3,则直接加到substr_len里面,否则substr_len只+2,并且更新longest_substr_len后substr_len要更新为2,因为又开始了一个新的substr。

class Solution {
public:
    /**
     * @param s: the string
     * @return: length of longest semi alternating substring
     */
    int longestSemiAlternatingSubstring(string &s) {
        int len = s.size();
        if (len == 0) return 0;
        int substr_len = 0, longest_substr_len = 0;
        vector<int> counts;
        int pos = 0, count = 0;
        while(pos < len) {
            if (s[pos] == 'a') {
                while (pos < len && s[pos] == 'a') {
                    count++;
                    pos++;
                }
                counts.push_back(count);
                count = 0;
            } else {
                while (pos < len && s[pos] == 'b') {
                    count++;
                    pos++;
                }
                counts.push_back(count);
                count = 0;
            }
        }

        for (int i = 0; i < counts.size(); ++i) {
            if (counts[i] < 3) {
                substr_len += counts[i];
                longest_substr_len = max(longest_substr_len, substr_len);
            }else {
                substr_len += 2;
                longest_substr_len = max(longest_substr_len, substr_len);
                substr_len = 2;
            }
        }
        return longest_substr_len;
    }
};



解法2:解法1的空间简化。
解法1需要额外的空间。我们可以直接扫描数组,如果当前字符和前一个字符相等则count++,否则count=0。当count<3时,每次substr_len增1,同时更新longest_substr_len; 如果count=3,只需将substr_len置2即可。注意这里为什么count=3不需要更新longest_substr_len呢?因为在count=2时已经更新了。

class Solution {
public:
    /**
     * @param s: the string
     * @return: length of longest semi alternating substring
     */
    int longestSemiAlternatingSubstring(string &s) {
        int len = s.size();
        if (len < 3) return 0;
        int substr_len = 1, longest_substr_len = 0;
        int pos = 1, count = 1;
        while(pos < len) {

            if (s[pos] == s[pos - 1]) {
                count++;
            } else {
                count = 1;
            }
            
            if (count < 3) {
                substr_len ++;
                longest_substr_len = max(longest_substr_len, substr_len);
            } else {
                substr_len = 2;
            }
            
            pos++;
        }

        return longest_substr_len;
    }
};

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值