给你一个只包含小写字母的字符串。
请你判断是否存在只在字符串中出现过一次的字符。
如果存在,则输出满足条件的字符中位置最靠前的那个。
如果没有,输出 no
。
输入格式
共一行,包含一个由小写字母构成的字符串。
数据保证字符串的长度不超过 100000。
输出格式
输出满足条件的第一个字符。
如果没有,则输出 no
。
输入样例:
abceabcd
输出样例:
e
#include <iostream>
using namespace std;
int main()
{
char c[100001]; /*字符串长度为100000,那么字符数组就多开一位
*/
int cnt[26]; /*这里cnt数组用来记住26个小写字母中每个字母出现的次数
相当于cnt[0]=a的次数,cnt[1]=b的次数,以此类推,就能得到输入的字符串中每个字母出现的次数
,然后再判断只出现一次的,然后依题意输出就行*/
cin >> c;
for (int i = 0; i < 26; i++)
{
cnt[i] = 0;
} /*这里是初始化数组,因为cnt数组每一个下标对应着一个字母,而每一次判断计算次数时,
每个字母的次数最后总会有一个结果,从而结束那一次的循环。若是不初始化cnt[i]=0的话
,这时cnt[i+1]最后得到的次数值就会是在原来cnt[i]的值上的基础上得到的,从而导致最后结果的错误,
*/
for (int i = 0; c[i]; i++)
cnt[c[i] - 'a']++;
/*这一步是用来求输入的字符串中每个小写字母对应的出现次数的,其中c[i]表示
是这个for循环的循环条件,意思是只要你输入的字符串没有\0字符,那么就都能输入。
这第二行是循环条件,cnt[c[i]-'a']表示的是字符数组的下标位对应的字母,用来统计这个位置上字母出现的次数,
例如两次都出现b,那么就会有cnt[b-'a']=cnt[1]++,因为是两次,所以最后得到的cnt的值为2,表示b出现了两次
,说白了就是字母与整数的交换运算,用asci码将两者联系了起来
*/
for (int i = 0; c[i]; i++)
if (cnt[c[i] - 'a'] == 1)
{
cout << c[i] << endl;
return 0; /*这里记得一定要写,表示找到了出现一次的字母就直接退出
程序,如果不写的话,会继续执行代码,再找下一个只出现一次的字母,
这与题目只找出现一次且第一次出现的字母不符合。
假如我没有写return 0,我输入abceabcd,那么会显示 e d no ,可以看出,
不仅只出现一次的字母都输出了,而且还执行了puts,这是输出不符合的,所以
这里必须要写return 0,因为这里不是switch case语句,可以用break,所以只能用
return 0了
*/
}
/*这一步就是判断字母是不是只出现了一次了,是的话就输出对应数组下标位的字母,
从而达到题目的目的
*/
puts("no"); // puts与printf和cout类似,都是输出,但是puts更简洁,能提高写代码的速度
return 0;
}
这代码里面有注释,希望大家不要嫌弃我啰嗦,我也是个刚学c++的小白,哪里不对还望大家指点啦,谢谢。