一切需要使用的 函数or语法:
to_string(a+b)
stoi(s)
stof(s,&idx) idx返回用了几个字符,0.12abc
tolower©
toupper©
getline(cin,s)
pos = s.find(‘.’)
printf(“%s”,s.c_str())
printf(“%.2lf”,double)
s.substr(pos,n) //不会改变s
1、字符串转换✔
to_string(a+b);
1001 A+B Format
#include<iostream>
#include<cstring>
using namespace std;
int main(){
int a,b;
cin>>a>>b;
int c=a+b;
string s = to_string(c);
string ans; //头插法
int cnt=0;
for(int i=s.size()-1;i>=0;i--){
res = s[i]+res;
cnt++;
if(cnt %3 ==0 && i && c[i-1] !='-') res =','+res;
}
cout<<s;
}
2、数字拼写✔
#include<iostream>
#include<vector>
#include<algorithm>
#include<numeric>
using namespace std;
int main()
{
vector<int> digits;
char digit;
while(cin>>digit){
digits.push_back(digit-'0');
}
int sum= accumulate(digits.begin(),digits.end(),0);
vector<string> numbers={"zero","one","two","three","four","five","six","seven","eight","nine"};
string ans=to_string(sum);
for(int i=0;i<ans.size();i++){
cout<<numbers[ ans[i]-'0'];
if(i!=ans.size()-1) cout<<" ";
}
}
3、签入与签出✔
最大值的初始化:if(!i || a[i]>max) max=a[i];
1006 Sign In and Sign Out
#include<iostream>
#include<cstring>
using namespace std;
int main()
{
int n;
cin>>n;
string id[n],in[n],out[n];
for(int i=0;i<n;i++){
cin>>id[i]>>in[i]>>out[i];
}
if(n==0) return 0;
int ansin,ansout;
string max,min;
for(int i=0;i<n;i++){
if(!i || in[i] < min) {
min = in[i];
ansin = i;
}
if(!i || out[i] > max) {
max = out[i];
ansout = i;
}
}
cout<<id[ansin]<<" "<<id[ansout]<<endl;
}
4、密码✔
难以辨认的字符的修改;
输入不用全存起来。
用临时变量存一下,然后根据需要才存入数组。int a[N],每次a[m]赋值,m++。
1035 Password
#include<iostream>
#include<vector>
#include<cstring>
using namespace std;
const int N = 1000+10;
int main(){
int n;
cin>>n;
string name[n],password[n];
vector<int> ans;
for(int i=0;i<n;i++){
cin>>name[i]>>password[i];
ans.push_back(i);
int sum=0;
for(auto &a : password[i]){
if(a=='1') a='@';
else if (a=='0') a='%';
else if (a=='l') a='L';
else if (a=='O') a='o';
else sum++;
}
if(sum==password[i].size() ) ans.pop_back();
}
int m=ans.size();
if (m==0) {
if(n==1) cout<<"There is 1 account and no account is modified";
else cout<< "There are " + to_string(n) + " accounts and no account is modified";
}
else{
cout<<m<<endl;
for(auto i:ans){
cout<<name[i]<<" "<<password[i]<<endl;
}
}
return 0;
}
5、最高分&最低分✔
个人觉得我自己这里处理的不错
1036 Boys vs Girls
#include<iostream>
#include<cstring>
using namespace std;
int main(){
int n;
cin>>n;
string fname,fid;int fscore=-1;
string mname,mid;int mscore=101;
for(int i=0;i<n;i++){
string name,id;
char gender;int score;
cin>>name>>gender>>id>>score;
if(gender=='F'){
if(score > fscore){
fscore = score;
fname = name;
fid = id;
}
}
else{
if(score < mscore){
mscore = score;
mname = name;
mid = id;
}
}
}
if(fscore==-1) cout<<"Absent"<<endl;
else cout<<fname<<" "<<fid<<endl;
if(mscore==101) cout<<"Absent"<<endl;
else cout<<mname<<" "<<mid<<endl;
if(fscore==-1 || mscore==101) cout<<"NA"<<endl;
else cout<<fscore-mscore<<endl;
return 0;
}
6、字符串减法✔
getline(cin,s)
unordered_set
1050 String Subtraction
#include<iostream>
#include<cstring>
#include<unordered_set>
using namespace std;
int main(){
string s1,s2;
getline(cin,s1);
getline(cin,s2);
unordered_set<char> S;
for(auto &c:s2){
S.insert(c);
}
string ans;
for(auto &c:s1){
if(S.count(c)==0) ans +=c;
}
cout<< ans << endl;
}
7、出现次数最多的单词⭐
大小写 tolower©、toupper©
通过双指针:外层 i 对不需要的过滤,内层 j 获取每一个单词。
出现次数最多(别给那套用map了)就正常一个unorder_map,然后遍历一遍,是On的,不然你排序是nlogn的
1071 Speech Patterns
#include<iostream>
#include<cstring>
#include<unordered_map>
using namespace std;
bool check(char c){
if(c>='0' && c<='9') return true;
else if(toupper(c)>='A' && toupper(c)<='Z') return true;
else return false;
}
int main (){
string s;
getline(cin,s);
unordered_map<string,int> words;
for(int i=0;i<s.size();i++){
if(check(s[i])){
string word;
int j=i;
while ( check(s[j]) && j<s.size() ) word+=tolower(s[j++]);
words[word]++;
i=j;
}
}
string answord;
int ans=-1;
for(auto &word:words){
if(word.second > ans || (word.second==ans && word.first<answord)){
answord=word.first;
ans = word.second;
}
}
cout<<answord<<" "<<ans<<endl;
}
8、解密-约会日期✔
#include<iostream>
#include<cstring>
using namespace std;
int main(){
string s1,s2,s3,s4;
cin>>s1>>s2>>s3>>s4;
int n=s1.size();
int i=0;
for(;i<n;i++){
if(s1[i]==s2[i]){
if(s1[i]=='A') cout<<"MON ";
else if(s1[i]=='B') cout<<"TUE ";
else if(s1[i]=='C') cout<<"WED ";
else if(s1[i]=='D') cout<<"THU ";
else if(s1[i]=='E') cout<<"FRI ";
else if(s1[i]=='F') cout<<"SAT ";
else if(s1[i]=='G') cout<<"SUN ";
else continue;
break;
}
}
i++;
for(;i<n;i++){
if(s1[i]==s2[i]){
if(s1[i] >='0' && s1[i]<='9') cout<<"0"<<s1[i]<<":";
else if(s1[i] >='A' && s1[i]<='N') cout<<10+(int)(s1[i]-'A')<<":";
else continue;
break;
}
}
n=s3.size();
for(int i=0;i<n;i++){
if(s3[i]==s4[i] && ( (s3[i]>='a' && s3[i]<='z')||(s3[i]>='A' && s3[i]<='Z') ) ) {
if(i<10) cout<<"0"<<i<<endl;
else cout<<i<<endl;
break;
}
}
}
9、电话账单✔
map里面放vector
y总计算费用(前缀和)好像确实比我方便很多。我自己的我写的什么JB,艹
1016 Phone Bills
//先将每个人的记录存储,然后排序进行筛选
#include<iostream>
#include<map>
#include<vector>
#include<algorithm>
#include<numeric>
#include<iomanip>
using namespace std;
vector<double> cost;
double day_cost;
struct Record{
string time;
string flag;
};
bool cmp(Record a,Record b){
return a.time<b.time;
}
void charge_day(string begin,string end,int &time,double &charge){
string beginh=begin.substr(0,2),endh=end.substr(0,2);
begin=begin.substr(3);
end=end.substr(3);
if(beginh==endh){
int temp=stoi(end)-stoi(begin);
time+=temp; //聊了30分钟
charge+=cost[stoi(beginh)]*temp;
}
else{
int h=stoi(beginh);
time+=60-stoi(begin);
charge+=cost[h]*(60-stoi(begin));
h++;
for(;h<stoi(endh);h++ ){
time+=60;
charge+=cost[h]*60;
}
time+=stoi(end);
charge+=cost[h]*stoi(end);
}
}
void charge(string begin,string end,double &total){ //这样有一个坏处,就是不能递归了
int time=0;
double charge=0;
//先算天
string beginday=begin.substr(0,2),endday=end.substr(0,2);
begin=begin.substr(3);
end=end.substr(3);
if( begin<=end){
time+=24*60*(stoi(endday)-stoi(beginday));
charge+=day_cost*(stoi(endday)-stoi(beginday));
charge_day(begin,end,time,charge);
}
else if(begin>end){
charge_day(end,begin,time,charge);
time = 24*60-time;
charge = day_cost-charge;
time+=24*60*(stoi(endday)-stoi(beginday)-1);
charge+=day_cost*(stoi(endday)-stoi(beginday)-1);
}
cout<<time<<" $"<<charge/100<<endl;
total+=charge;
}
int main()
{
cout<<setiosflags( ios::fixed )<<setprecision(2);
//1 初始化cost
for(int i=0;i<24;i++){
double temp;
cin>>temp;
cost.push_back(temp);
}
day_cost=60*accumulate(cost.begin(),cost.end(),0);
//2 构建存储结构
int k;
cin>>k;
map<string,vector<Record> > data;
//2.1 先储存信息 ,后计算总时间和价格 data[lili]=vector< 1/22 17.30 >
for(int i=0;i<k;i++){
string name;
Record record;
cin>>name>>record.time>>record.flag;
// if( !data.count(name) ){
// vector<Record> ini;
// data[name]=ini;
// }
data[name].push_back(record);
}
//2.2 排序
for(auto it=data.begin();it!=data.end();it++){
sort( (it->second).begin(), (it->second).end(),cmp );
}
//2.3 删除无效项
for(auto it=data.begin();it!=data.end();it++){
//对于每个name进行遍历
for(auto itv=it->second.begin();itv!=it->second.end();){
//成对的找,如果当前一对【1,2】不满足条件,删除1,继续找【2,3】
if( itv == it->second.end()-1 ) it->second.erase(itv);
else if( !(itv->flag=="on-line" && (itv+1)->flag=="off-line") ) it->second.erase(itv);
else{
itv+=2;
}
}
}
//二**直接对data中的数据进行加工输出即可*************************************************************************************
for(auto it=data.begin();it!=data.end();it++){
if(it->second.size()==0) continue;
//输出每个人的标题
string month= it->second[0].time.substr(0,2);
cout<<it->first<<" "<<month<<endl;
//逐项输出账单,并记录总账单。
double total=0;
for(auto itv=it->second.begin();itv!=it->second.end();){
//获取前后时间
string begin=itv->time.substr(3);
itv++;
string end=itv->time.substr(3);
itv++;
//统计信息
cout<<begin<<" "<<end<<" ";
charge(begin,end,total); //计算后函数中直接输出
}
//cout<<"Total amount: $"<<total/100<<endl;
printf("Total amount: $%.2f", total/100.00);
cout<<endl;
}
}
10、银行排队✔
时间用秒计时;堆里存的是当前窗口的预计的开始服务的时间;
对于每个客户,根据now 与 peoples[i].arrive_time 判断来早了还是来晚了。
来早了,无等待时间,并加入堆中,他被服务完的时刻是peoples[i].server_time + now
来晚了,新增等待时间,加入堆中。他被服务完的时刻是peoples[i].server_time + peoples[i].arrive_time
1017 Queueing at Bank
#include<iostream>
#include<algorithm>
#include<queue>
using namespace std;
const int N = 10000+10;
int n,k;
struct People{
int arrive_time;
int server_time;
bool operator < (People x){
return arrive_time<x.arrive_time;
}
}peoples[N];
int main(){
cin>>n>>k;
for(int i=0;i<n;i++){
int h,m,s,l;
scanf("%d:%d:%d %d",&h,&m,&s,&l);
int arrive_time,server_time;
arrive_time = h*3600 + m*60 + s;
server_time = min(l,60) * 60;
peoples[i] = {arrive_time,server_time};
}
sort(peoples,peoples+n);
priority_queue<int,vector<int>,greater<int> > windows; //堆里存的是当前窗口的预计的开始服务的时间
for(int i=0;i<k;i++) windows.push(8*3600);
int wait_time=0;
int ignore=0;
for(int i=0;i<n;i++){
if(peoples[i].arrive_time > 17*3600) {
ignore++;
continue;
}
int now = windows.top();windows.pop();
if(now >= peoples[i].arrive_time){
wait_time += now - peoples[i].arrive_time;
windows.push(now + peoples[i].server_time);
}
else {
windows.push(peoples[i].arrive_time + peoples[i].server_time);
}
}
printf("%.1lf\n",(double)(wait_time )/60.0 /(n-ignore) );
}
11、乒乓球
12、 转化为科学计数法✔
pos = s.find(‘.’);去除小数点;
1060 Are They Equal
#include<iostream> //科学计数法 ,N表示现实多少位
using namespace std; //先去掉前置0 (如果是0.004这种)还需要判断后继续去前置0
//之后分别计算数字部分和指数部分就行了
string solve(int N,string s){
int exp=0;
while(s.size() >0 && s[0]=='0'){
s.erase(s.begin());
}
if(s[0] =='.'){ //去掉前导0是小数点,说明s后面是小数
s.erase(s.begin());
while(s.size() >0 && s[0]=='0'){
s.erase(s.begin());
exp--;
}
}
else{ //说明是整数部分
int i=0;
for( ;i<s.size() && s[i]!='.';i++){
exp++;
}
if(i<s.size()){
s.erase(s.begin()+i);
}
//删除这个小数点即可,得到想要的整个数字部分。因为咱们指数已经确定了
//或者你在后面读取的时候对小数点进行讨论,但可能更麻烦
}
if(s.size()==0) exp=0;
//已经将字符串处理完,现在仅包含数字部分(指数已确定所以不用管),且为空的话,重新更新指数为0.
string ans="";
for(int i=0,k=0;k<N;i++,k++){ //补0操作
if( i <s.size() ) ans+=s[i]; //如果字符串没结束,赋值
else ans+='0'; // 如果结束了,补0
}
ans="0."+ans+"*10^"+to_string(exp);
return ans;
}
int main()
{
int N;
string A,B,resA,resB;
cin>>N>>A>>B;
resA = solve(N,A);
resB = solve(N,B);
if(resA==resB)
cout<<"YES "<<resA<<endl;
else
cout<<"NO "<<resA<<" "<<resB<<endl;
return 0;
}
13. 科学计数法转化为传统计数✔
记录正负号;
指数部分根据 正负分别处理。
指数为正时,可能消除小数点,也要分两种情况处理。
1073 Scientific Notation
#include<iostream>
#include<cstring>
using namespace std;
int main(){
string s;
cin>>s;
int flag=false;
if(s[0]=='-') flag=true;
s=s.substr(1);
int e_pos = s.find('E');
if(s[e_pos+1]=='-'){
int n = stoi(s.substr(e_pos+2))-1; //这里默认指数>0
s = s.substr(0,e_pos);
s = s.substr(0,1) + s.substr(1+1,e_pos-2);
while(n--){
s = "0" +s;
}
s= "0."+s;
}
else {
int n = stoi(s.substr(e_pos+2)); //这里默认指数>0
s = s.substr(0,e_pos);
if(n+2 >= s.size() ){ //没有小数点
n = n+2-s.size();
s = s.substr(0,1) + s.substr(1+1,e_pos-2);
while(n--){
s = s +"0";
}
}
else{ //有小数点
s = s.substr(0,1) + s.substr(1+1,e_pos-2);
s = s.substr(0,n+1) +"." + s.substr(n+1);
}
}
if(flag) s = '-'+s;
cout<<s<<endl;
}
14. Kuchiguse✔
字符串结尾口头禅。
1077 Kuchiguse
#include<iostream>
#include<cstring>
#include<algorithm>
using namespace std;
const int N = 110;
int n;
char ans[257];
int k;
int main(){
cin>>n;
string a;getline(cin,a);
for(int i=0;i<n;i++){
string s;
getline(cin,s);
reverse(s.begin(),s.end());
if(i==0){
for(int j =0;j<s.size();j++) ans[j]=s[j];
k=s.size();
}
else{
int j=0;
for(;j<k && j<s.size();j++){
if(ans[j]!=s[j] ) {
break;
}
}
k=j;
}
}
if(k==0) cout<<"nai"<<endl;
else{
for(int i=k-1;i>=0;i--){
cout<<ans[i];
}
cout<<endl;
}
}
15. 中文读数字
全是特殊情况,判断处理。
1082 Read Number in Chinese
16、坏掉的键盘✔
逗号运算符!!!
双指针
1084 Broken Keyboard
#include<iostream>
#include<unordered_set>
#include<cstring>
using namespace std;
int main(){
string s1,s2;
cin>>s1>>s2;
int i=0,j=0;
unordered_set<char> S;
while(i<s1.size()){
char x = toupper(s1[i]);
char y = toupper(s2[j]);
if(x==y) j++;
else{
if(S.count(x)==0) cout<<x,S.insert(x);
}
i++;
}
cout<<endl;
}
17、判断实数是否合法 ⭐
try_catch 实现;
stof的用法
pos=s.find(‘.’)
%.2lf
1108 Finding Average
#include<iostream>
#include<cstring>
using namespace std;
bool check(string s){
try{
size_t idx;
double x = stof(s,&idx);
if(idx<s.size()) return false;
if(x<-1000 || x>1000) return false;
int pos = s.find('.');
if(pos!=-1 && idx-pos-1>2) return false;
}
catch(...){
return false;
}
return true;
}
int main(){
int n;
cin>>n;
int cnt=0;double sum=0;
for(int i=0;i<n;i++){
string s;
cin>>s;
if(check(s)) sum+=stof(s),cnt++;
else cout<<"ERROR: "<<s<<" is not a legal number"<<endl;
}
if(cnt==0) cout<<"The average of 0 numbers is Undefined"<<endl;
else if(cnt==1) cout<<"The average of 1 number is ",
printf("%.2lf\n",sum);
else
cout<<"The average of "<<cnt<<" numbers is ",
printf("%.2lf\n",sum/cnt);
}
18、间隔抽奖✔
1124 Raffle for Weibo Followers
#include<iostream>
#include<cstring>
#include<unordered_set>
using namespace std;
int main(){
int n,skip,pos;
cin>>n>>skip>>pos;
pos--;
unordered_set<string> S;
for(int i=0;i<n;i++){
string name;
cin>>name;
if( i==pos ) {
if( S.count(name)==0 ) cout<<name<<endl,S.insert(name);
else pos-=skip-1;
pos+=skip;
}
}
if(S.empty()==1) cout<<"Keep going..."<<endl;
}
19、学校排名⭐
比较经典的一个题目
1:用map存键值对。
2:map中的值用 struct结构体存。
3:遍历map中的值存入vector进行sort排序。
4:重载结构体的比较运算符。
5:double转int 的精度需要加1e-8。
6:计算排名的rank计算。
1141 PAT Ranking of Institutions
#include<iostream>
#include<cstring>
#include<vector>
#include<unordered_map>
#include<algorithm>
using namespace std;
struct school{
string name;
double score;
int cnt;
bool operator < (school a){
if(a.score!=score) return score>a.score;
else if(a.cnt!=cnt) return cnt < a.cnt;
else return name<a.name;
}
};
int main(){
int n;
cin>>n;
unordered_map<string,school> ans1;
vector<school> ans2;
for(int i=0;i<n;i++){
string id,institute;double score;
cin>>id>>score>>institute;
for(int i=0;i<institute.size();i++) institute[i]=tolower(institute[i]);
ans1[institute].name=institute;
ans1[institute].cnt+=1;
if(id[0]=='B') ans1[institute].score+=score/1.5;
else if (id[0]=='A') ans1[institute].score+=score;
else if (id[0]=='T') ans1[institute].score+=score*1.5;
}
for(auto &m :ans1){
m.second.score = (int) (m.second.score +1e-8);
ans2.push_back(m.second);
}
sort( ans2.begin(),ans2.end() );
int rank=1;
cout<<ans2.size()<<endl;
for(int i=0;i<ans2.size();i++){
if((int)ans2[i].score != (int)ans2[i-1].score) rank = i+1;
cout<<rank<<" "<<ans2[i].name<<" "<<(int)ans2[i].score<<" "<<ans2[i].cnt<<endl;
}
}
20、PAT准考证信息统计✔
会了上题的经典之后,这一题虽然多,但都是一个逻辑了。
另外一点是,这一点用cout会超时,改成printf过了。。。
s.substr(pos,n) //不会改变s
1153 Decode Registration Card of PAT
#include<iostream>
#include<cstring>
#include<vector>
#include<algorithm>
#include<unordered_map>
using namespace std;
const int N=10000+10,M=110;
int n,m;
string id[N];int score[N];
struct person{
string id;
int score;
bool operator < (person t){
if(score != t.score) return score>t.score;
else return id < t.id;
}
};
struct Site{
string site;
int cnt;
bool operator < (Site s){
if(cnt!=s.cnt) return cnt> s.cnt;
else return site<s.site;
}
};
void query1(string order){
vector<person> persons;
for(int i=0;i<n;i++){
person t;
t.id=id[i];
t.score=score[i];
if(id[i][0]==order[0]) persons.push_back(t);
}
if(persons.size()==0) printf("NA\n");
else{
sort(persons.begin(),persons.end());
for(auto &t:persons){
printf("%s %d\n",t.id.c_str(),t.score);
}
}
}
void query2(string order){
int cnt=0;int sum=0;
for(int i=0;i<n;i++){
if( id[i].substr(1,3) == order){
cnt++;
sum+=score[i];
}
}
if(cnt==0) cout<<"NA"<<endl;
else
cout<<cnt<<" "<<sum<<endl;
}
void query3(string order){
unordered_map<string,int> date;
for(int i=0;i<n;i++){
string site=id[i].substr(1,3);
if( id[i].substr(4,6) == order){
date[site]+=1;
}
}
vector<Site> sites;
for(auto &m:date){
Site site;
site.site = m.first;
site.cnt = m.second;
sites.push_back(site);
}
if(sites.size()==0) cout<<"NA"<<endl;
else{
sort(sites.begin(),sites.end());
for(auto &t:sites){
printf("%s %d\n",t.site.c_str(),t.cnt);
}
}
}
int main(){
cin>>n>>m;
for(int i=0;i<n;i++){
cin>>id[i]>>score[i];
}
for(int i=0;i<m;i++){
int type;string order;
cin>>type>>order;
cout<<"Case "<<i+1<<": "<<type<<" "<<order<<endl;
if(type==1) query1(order);
else if(type==2) query2(order);
else if(type==3) query3(order);
}
return 0;
}