字符串去重、统计不同字符种类数问题
1、編寫一個函數,計算字符串中含有的不同字符的個數。字符在ACSII碼范圍內(0~127),不在范圍內的不作統計。
#include <iostream>
#include <string>
using namespace std;int main(){string str;int m,len,count=1;int flag = 0; //定義一個信號參數cin >> str;len = str.size();for(int i=0;i<len;++i){ //判斷字符串中是否存在范圍內字符,有則作為參照字符if(str[i]<128&&str[i]>=0){m = i;}else{flag = 1; //若是所有字符均不在范圍類,傳遞信號結束程序}}if(flag == 0){ for(int i=0;i<len-1;++i){ //先對字符串去超范圍字符和重復字符,將不合要求的、重復的字符全部置為某個已存在的參照字符if(str[i]<128&&str[i]>=0){for(int j=i+1;j<len;++j){if(str[i]==str[j]){str[j]=str[m];}}}else{str[i]= str[m];}}for(int i=0;i<len;++i){ //對去重后的范圍內字符串求不同字符個數if(str[i]!=str[m]){count++;}}}else{count = 0;}cout << count << endl;return 0;
}
本題涉及到ASCII碼表的的知識,需要考慮的情形比較多,首先是尋找范圍內的參照字符順便判斷是否所有字符均在范圍之外,因此定義信號參數。其次是去除重復、去除范圍外的字符,最后遍歷所有字符,得到不同字符的種類數目。
2、寫出一個程序,接受一個(由字母和數字組成)字符串和一個字符,然后輸出輸入字符串中含有該字符的個數(不區分大小寫)。
#include <iostream>
#include <string>using namespace std;
int main(){int len,count=0;string str,c;cin >> str;len = str.size();cin >> c;for(int i=0;i<len;++i){if(str[i]==c[0]){count++; }}cout << count << endl;return 0;
}
第一次編寫這個程序時,直接考慮用string對象對字符和字符串進行比較操作,但是這種情形下,所有case的通過率為90%。是因為沒有考慮大小寫不區分的情形。本題也用到了ASCII碼的相關知識,比較常見的知識點有:ASCII碼0為空字符,ASCII碼48~57為數字0~9,ASCII碼65~90為字母A~Z,ASCII碼97~122為字母a~z。加入對輸入字符的判斷
#include <iostream>
#include <string>
using namespace std;int main(){int len,count=0;string str,c;cin >> str;len = str.size();cin >> c;if(c[0]>64){ //若遍歷尋找的目標字符是字母,那么要考慮字符串中字符ASCII碼必須大于64for(int i=0;i<len;++i){if((str[i]==c[0]||str[i]+32==c[0]||str[i]-32==c[0])&&str[i]>64){ //無論字符串中字母是否大小寫,考慮三種情形count++;}}}else{for(int i=0;i<len;++i){ //若輸入字符為數字,那么字符串中字符只要與之相等即可if((str[i]==c[0]){count++;}}}cout << count << endl;return 0;
}
3、一道網易的字符串情景題:小易有一些彩色的磚塊。每種顏色由一個大寫字母表示。各個顏色磚塊看起來都完全一樣。現在有一個給定的字符串s,s中每個字符代表小易的某個磚塊的顏色。小易想把他所有的磚塊排成一行。如果最多存在一對不同顏色的相鄰磚塊,那么這行磚塊就很漂亮的。請你幫助小易計算有多少種方式將他所有磚塊排成漂亮的一行。(如果兩種方式所對應的磚塊顏色序列是相同的,那么認為這兩種方式是一樣的。)
例如: s = "ABAB",那么小易有六種排列的結果:
"AABB","ABAB","ABBA","BAAB","BABA","BBAA"
其中只有"AABB"和"BBAA"滿足最多只有一對不同顏色的相鄰磚塊。
#include <iostream>
using namespace std;void func(string&,int);
int main(){string str;int len;cin >> str;len = str.size();func(str,len);return 0;
}
void func(string& s,int length){ //定義一個字符串處理函數,傳入string對象引用和string對象大小參數 int d, count = 0;for(int i=1;i<length-1;i++){ //第一步,去重,將重復的字符串全部置為首字符for(int j=i+1;j<length;j++){if(s[i]==s[j]){s[j]=s[0];}}}for(int i=1;i<length;i++){ //第二步,統計不同于首字符的字符個數即為字符串中字符種類數目if(s[i]!=s[0]){count++;}}if(count > 1){cout << '0' << endl ;}else if(count == 0){cout << '1' << endl ;}else{cout << '2' << endl ;}}
本題題目結合了具體情境,抽象為字符串處理的程序之后,則比較簡單。不外乎去重,統計字符串中不同字符的數目,因為磚的擺放方法只與顏色數目(字符種類)有關,因此轉化為統計不同字符的數目即可。
4、找出字符串中第一個只出現一次的字符(考慮多個字符串輸入)
#include<iostream>
#include<string>
using namespace std;int main(){string str;while(cin >> str){int len,count = 0;int flag = 0; //定義一個信號參數,在去重置空的兩層循環中傳遞信號len = str.size();for(int i=0;i<len-1;i++){ //先將重復的字符全部置為空for(int j=i+1;j<len;j++){if(str[i]==str[j]){str[j]='\0';flag ++;}}if(flag > 0){str[i]='\0';flag = 0;}}for(int i=0;i<len;++i){ //遍歷字符串輸出第一個不為空的字符串if(str[i]!='\0'){cout << str[i] << endl;;count ++;break;}}if(count == 0){ //如果遍歷字符串全部為空,則不存在“唯一”的字符cout << "-1" << endl;}}return 0;
}
之前在編寫此程序時,牛客網上總顯示通過case為90%,后來仔細檢查才發現count初始化在while()語句之前,因此前一個字符串遍歷后的count值會保留到之后的測試,所以出錯。
編譯和調試結果:
總結
以上是生活随笔為你收集整理的字符串去重、统计不同字符种类数问题的全部內容,希望文章能夠幫你解決所遇到的問題。