题目描述
字符串 S 由小写字母组成。我们要把这个字符串划分为尽可能多的片段,同一字母最多出现在一个片段中。返回一个表示每个字符串片段的长度的列表。
解题思路
从贪心的角度来说,本题应该选取尽量小的片段,保证片段数量尽可能多。
先去计算得到每个字母最后出现的位置,显而易见的是,一个字母的起点start和终点end肯定在同一个片段内,但是end的位置不一定是这个片段的终点。
举个栗子:
s = "absghab"
这个片段的起始字母是a,但是终点是b。
所以在遍历整个数组的时候,end需要不段更新。
end = max(end,map[S[i] - 'a'])
// map[S[i] - 'a']是S[i]这个字母的最终位置
代码
class Solution {
public:
vector<int> partitionLabels(string S) {
// 遍历字符串,得到下标位置
vector<int> map(26, 0); // 创建一个大小为26,全0的容器
for (int i = 0; i < S.size(); ++i) { // 这个个要记住,求元素最远下标
map[S[i] - 'a'] = i; // 字母最后位置 因为map是可以改变的
//可是有一点,没有出现过的字母的位置会被默认为0,如果a的最终位置也是0 会不会有歧义?
}
vector<int> result; // 创建一个容器 去获得结果
int start = 0, end = 0; //起始和终点下标 开始时为0
// 循环遍历
for (int i = 0; i < S.size(); ++i) {
end = std::max(end, map[S[i] - 'a']); // 不断去迭代end end应该是整个区间所有元素最终位置最大的那个的终点下标
if(i==end){ //如果达到了最远位置 则此区间划分成功
result.push_back(end - start + 1);
start = i + 1;
}
}
return result;
}
};
继续努力,未来是星辰大海!