LeetCode | 767. Reorganize String调整字符串使得字符串相同字符不相邻
2018-02-04 15:27
411 查看
Givena string S, check if the letters can berearranged so that two characters that are adjacent
to each other are not thesame.
Ifpossible, output any possible result. If not possible, return the emptystring.
Example 1:
Input: S = "aab"
Output: "aba"
Example 2:
Input: S = "aaab"
Output: ""
Note:
S will consist of lowercase letters and have length in range [1, 500].
这一题明明知道怎么做,但是由于思路不清晰,改了好多次,很烦
这一题首先需要明白,可以证明,当s中每一个字母的个数都小于等于其他字母个数之和减一的时候,一定存在一个方案可以使得字符串S的每一个字母不相邻,方法是,使用一个数组theLetter存储s中每一个字母的出现的次数,然后每次取theLetter中的前两个不为0的位置的值,将里面的字母交替放入result,然后取theLetter后两个值,交替放入result。。。一直持续这个过程,直到theLetter中只剩下一个不为0的组,然后把这个组的字母按照从前往后的顺序交替放入S的前面,假如能够放入而不产生冲突,那么S一定存在一种方案,如果产生冲突,那么S一定有一组的个数大于其他所有组的个数之和加一,那么一定不存在可行的方案
当对于某个问题想解决方法的时候,当有一种方法,当产生结果A的时候一定有解,当产生结果B的时候解一定不存在,那么这种方法可以直接被使用,不需要去证明!
class Solution {
public:
stringreorganizeString(string S) {
int theLetter[26] = { 0 };
string result = "";
int theLastI = 0; int theLNeed = 0; chartheNeedC;
for (int i = 0; i < S.size(); i++)
{
theLetter[S[i] - 'a']++;
}
for (int i = 0; i < 26; i++)
if (theLetter[i] != 0) theLastI = i;
int indexOne=0, indexTwo=0;
while(indexOne<26&&theLetter[indexOne] == 0) indexOne++;
indexTwo = indexOne; indexTwo++;
while (indexTwo < 26 &&theLetter[indexTwo] == 0) indexTwo++;
while (indexTwo < 26)
{
if (indexTwo == theLastI)
{
if (theLetter[indexOne] >theLetter[indexTwo])
{
theLNeed =theLetter[indexOne] - theLetter[indexTwo]-1;
theNeedC = indexOne +'a';
if (theLNeed >result.size()) return "";
}
else
{
theLNeed =theLetter[indexTwo] - theLetter[indexOne];
theNeedC = indexTwo +'a';
if (theLNeed >result.size()+1) return "";
}
}
while (1)
{
result.push_back(indexOne +'a'); theLetter[indexOne]--;
if (theLetter[indexOne] == 0)break;
result.push_back(indexTwo +'a');
theLetter[indexTwo]--;
if (theLetter[indexTwo] == 0) break;
}
if(theLetter[indexOne] != 0)
{
if(indexTwo==theLastI)result.push_back(indexOne + 'a');
while (indexTwo < 26&& theLetter[indexTwo] == 0) indexTwo++;
}
else
{
if (indexTwo == theLastI)result.push_back(indexTwo + 'a');
indexOne = indexTwo++;
while (indexTwo < 26&& theLetter[indexTwo] == 0) indexTwo++;
}
}
indexOne = 0;
for (int i = 0; i < theLNeed; i++)
{
result.insert(result.begin() +indexOne, theNeedC);
indexOne += 2;
}
return result;
}
};
to each other are not thesame.
Ifpossible, output any possible result. If not possible, return the emptystring.
Example 1:
Input: S = "aab"
Output: "aba"
Example 2:
Input: S = "aaab"
Output: ""
Note:
S will consist of lowercase letters and have length in range [1, 500].
这一题明明知道怎么做,但是由于思路不清晰,改了好多次,很烦
这一题首先需要明白,可以证明,当s中每一个字母的个数都小于等于其他字母个数之和减一的时候,一定存在一个方案可以使得字符串S的每一个字母不相邻,方法是,使用一个数组theLetter存储s中每一个字母的出现的次数,然后每次取theLetter中的前两个不为0的位置的值,将里面的字母交替放入result,然后取theLetter后两个值,交替放入result。。。一直持续这个过程,直到theLetter中只剩下一个不为0的组,然后把这个组的字母按照从前往后的顺序交替放入S的前面,假如能够放入而不产生冲突,那么S一定存在一种方案,如果产生冲突,那么S一定有一组的个数大于其他所有组的个数之和加一,那么一定不存在可行的方案
当对于某个问题想解决方法的时候,当有一种方法,当产生结果A的时候一定有解,当产生结果B的时候解一定不存在,那么这种方法可以直接被使用,不需要去证明!
class Solution {
public:
stringreorganizeString(string S) {
int theLetter[26] = { 0 };
string result = "";
int theLastI = 0; int theLNeed = 0; chartheNeedC;
for (int i = 0; i < S.size(); i++)
{
theLetter[S[i] - 'a']++;
}
for (int i = 0; i < 26; i++)
if (theLetter[i] != 0) theLastI = i;
int indexOne=0, indexTwo=0;
while(indexOne<26&&theLetter[indexOne] == 0) indexOne++;
indexTwo = indexOne; indexTwo++;
while (indexTwo < 26 &&theLetter[indexTwo] == 0) indexTwo++;
while (indexTwo < 26)
{
if (indexTwo == theLastI)
{
if (theLetter[indexOne] >theLetter[indexTwo])
{
theLNeed =theLetter[indexOne] - theLetter[indexTwo]-1;
theNeedC = indexOne +'a';
if (theLNeed >result.size()) return "";
}
else
{
theLNeed =theLetter[indexTwo] - theLetter[indexOne];
theNeedC = indexTwo +'a';
if (theLNeed >result.size()+1) return "";
}
}
while (1)
{
result.push_back(indexOne +'a'); theLetter[indexOne]--;
if (theLetter[indexOne] == 0)break;
result.push_back(indexTwo +'a');
theLetter[indexTwo]--;
if (theLetter[indexTwo] == 0) break;
}
if(theLetter[indexOne] != 0)
{
if(indexTwo==theLastI)result.push_back(indexOne + 'a');
while (indexTwo < 26&& theLetter[indexTwo] == 0) indexTwo++;
}
else
{
if (indexTwo == theLastI)result.push_back(indexTwo + 'a');
indexOne = indexTwo++;
while (indexTwo < 26&& theLetter[indexTwo] == 0) indexTwo++;
}
}
indexOne = 0;
for (int i = 0; i < theLNeed; i++)
{
result.insert(result.begin() +indexOne, theNeedC);
indexOne += 2;
}
return result;
}
};
相关文章推荐
- 387.leetcode First Unique Character in a String(easy)[统计字符串字符次数]
- [leetcode 318]Maximum Product of Word Lengths--判断两个字符串是否有相同的字符
- 汇编语言: 试编写一段程序,要求比较两个字符串 string1 和 string2 所含字符是否相等,如相 等则显示“MATCH”, 若不相同则显示“NO MATCH”。
- LeetCode number387 字符串第一个没有相同的字符
- java编程---3.3 (关于String/for的练习题) 提取字符串中连续相同的字符,例如:把aabbaaccbbbm变成2a2b2a2c3bm
- LeetCode Reverse Vowels of a String(字符串中元音字符反转)
- 从字符串中删除相同的相邻字符
- LeetCode-49 Anagrams(返回字符相同的字符串)
- 【leetcode】(Python)Reverse Vowels of a String实现字符串内元字符倒序
- LeetCode 8. String to Integer (atoi) C++ --字符串转为数字,包含正负号、空格、字母、数字等字符
- 6-2-1 字符串-字符串变量String-创建字符串变量-初始化字符串变量-字符串连接-输入字符串(单词、行)-对象变量的赋值-比较两个字符串是否同一个-比较两个字符串内容是否相同
- 每天一道LeetCode-----将字符串的连续相同的字符合并成一个字符后加个数
- 字符串处理的两个问题:删除指定字符,删除相邻相同的字符
- [LeetCode] First Unique Character in a String 字符串第一个不同字符
- C#List转字符串,字符串转List,字符数组转Int数组,字符串转string,取某一位置字符等
- 字符数组和字符串,char 和string定义的字符串的区别与遍历
- JavaSE8基础 String indexOf 正向 从指定索引值开始查找 字符在字符串中第一次出现的位置
- LeetCode 之 string字符串一
- leetcode -- 434. Number of Segments in a String 【字符串处理】
- c# stream byte char string 流、字节、字符、字符串