
【新手上路】洛谷入门5:字符串题单题解
亦余心之所善兮,虽九死其犹未悔。
·
亦余心之所善兮,虽九死其犹未悔。
文章目录
-
- [P5733 自动修正](https://www.luogu.com.cn/problem/P5733)
- [P1914 小书童——凯撒密码](https://www.luogu.com.cn/problem/P1914)
- [P1125 笨小猴](https://www.luogu.com.cn/problem/P1125)
- [P1957 口算练习题](https://www.luogu.com.cn/problem/P1957)
- [P5015 标题统计](https://www.luogu.com.cn/problem/P5015)
- [P5734 文字处理软件](https://www.luogu.com.cn/problem/P5734)
- [P1308 统计单词数](https://www.luogu.com.cn/problem/P1308)
- [P1765 手机](https://www.luogu.com.cn/problem/P1765)
- [P3741 小果的键盘](https://www.luogu.com.cn/problem/P3741)
- [P1321 单词覆盖还原](https://www.luogu.com.cn/problem/P1321)
- [P1553 数字反转(升级版)](https://www.luogu.com.cn/problem/P1553)
- [P1603 斯诺登的密码](https://www.luogu.com.cn/problem/P1603)
- [P1200 你的飞碟在这儿](https://www.luogu.com.cn/problem/P1200)
- [P1597 语句解析](https://www.luogu.com.cn/problem/P1597)
- [P1598 垂直柱状图](https://www.luogu.com.cn/problem/P1598)
P5733 自动修正
• 将字符串中所有小写字母转换为大写,直接遍历处理每个字符即可。
代码如下:
#include <bits/stdc++.h>
using namespace std;
int main() {
string s; cin >> s;
for (char &c : s) c = toupper(c);
cout << s;
}
P1914 小书童——凯撒密码
• 每个字母循环右移n位,注意用模26运算处理越界。
代码如下:
#include <bits/stdc++.h>
using namespace std;
int main() {
int n; string s;
cin >> n >> s;
for (char &c : s)
c = (c-'a'+n)%26 + 'a';
cout << s;
}
P1125 笨小猴
• 统计字母频率,计算极差后用筛法判断素数。
代码如下:
#include <bits/stdc++.h>
using namespace std;
int main() {
string s; cin >> s;
int cnt[26]={0}, mx=0, mn=100;
for(char c:s) cnt[c-'a']++;
for(int n:cnt) if(n) {
mx = max(mx,n);
mn = min(mn,n);
}
int d=mx-mn;
vector<bool> isp(max(2,d+1),1);
for(int i=2;i*i<=d;++i) if(isp[i])
for(int j=i*i;j<=d;j+=i) isp[j]=0;
cout << (d>1&&isp[d]?"Lucky Word":"No Answer") << '\n' << (d>1?d:0);
}
P1957 口算练习题
• 根据输入格式动态判断运算符,使用字符串流处理类型转换。
代码如下:
#include <bits/stdc++.h>
using namespace std;
int main() {
int n; cin >> n;
char op; string a, b;
while(n--) {
cin >> a;
if(isalpha(a[0])) {
op = a[0];
cin >> a >> b;
} else {
cin >> b;
swap(a,b);
}
int x=stoi(a), y=stoi(b), res;
if(op=='a') res=x+y, op='+';
else if(op=='b') res=x-y, op='-';
else res=x*y, op='*';
string expr = a+op+b+"="+to_string(res);
cout << expr << '\n' << expr.size() << '\n';
}
}
P5015 标题统计
• 统计有效字符数(字母/数字),注意getline读取整行。
代码如下:
#include <bits/stdc++.h>
using namespace std;
int main() {
string s; getline(cin,s);
int cnt=0;
for(char c:s)
cnt += isalnum(c)>0;
cout << cnt;
}
P5734 文字处理软件
• 模拟四个字符串操作指令,注意substr的用法。
代码如下:
#include <bits/stdc++.h>
using namespace std;
int main() {
int q; string s; cin >> q >> s;
while(q--) {
int op; cin >> op;
if(op==1) {
string t; cin >> t;
s += t;
} else if(op==2) {
int a,b; cin >> a >> b;
s = s.substr(a,b);
} else if(op==3) {
int a; string t; cin >> a >> t;
s.insert(a,t);
} else {
string t; cin >> t;
cout << (int)s.find(t) << '\n';
}
if(op!=4) cout << s << '\n';
}
}
P1308 统计单词数
• 在单词前后添加空格确保完全匹配,注意大小写转换。
代码如下:
#include <bits/stdc++.h>
using namespace std;
int main() {
string t, s;
getline(cin,t); getline(cin,s);
for(char &c:t) c = tolower(c);
for(char &c:s) c = tolower(c);
t = " "+t+" "; s = " "+s+" ";
int pos = s.find(t), cnt = 0, first = pos;
while(pos != -1) {
cnt++;
pos = s.find(t, pos+1);
}
if(cnt) cout << cnt << " " << first;
else cout << -1;
}
P1765 手机
• 预存每个字母的按键次数,遍历累加即可。
代码如下:
#include <bits/stdc++.h>
using namespace std;
int main() {
int cnt[] = {1,2,3,1,2,3,1,2,3,1,2,3,1,2,3,1,2,3,4,1,2,3,1,2,3,4};
string s; getline(cin,s);
int ans=0;
for(char c:s)
ans += (c==' ') ? 1 : cnt[c-'a'];
cout << ans;
}
P3741 小果的键盘
• 先处理所有VK,再检查是否有剩余可转换的连续相同字符。
代码如下:
#include <bits/stdc++.h>
using namespace std;
int main() {
int n; string s; cin >> n >> s;
int cnt=0;
for(int i=0;i<n-1;++i)
if(s[i]=='V' && s[i+1]=='K') {
cnt++;
s[i]=s[i+1]='_';
}
for(int i=0;i<n-1;++i)
if(s[i]!='_' && s[i]==s[i+1]) {
cnt++;
break;
}
cout << cnt;
}
P1321 单词覆盖还原
• 遍历字符串,统计"boy"和"girl"的覆盖情况。
代码如下:
// #include <bits/stdc++.h>
// using namespace std;
// int main()
// {
// int cnt_b=0,cnt_g=0;
// string s;
// cin >> s;
// int pos1=s.find("boy");
// while(pos1!=-1)
// {
// s[pos1] = s[pos1+1] = s[pos1+2] = '.';
// cnt_b++;
// pos1 = s.find("boy",pos1);
// }
// int pos2 = s.find("bo");
// while(pos2!=-1)
// {
// s[pos2] = s[pos2+1] = '.';
// cnt_b++;
// pos2 = s.find("bo",pos2);
// }
// int pos3 = s.find("oy");
// while(pos3!=-1)
// {
// s[pos3] = s[pos3+1] = '.';
// cnt_b++;
// pos3 = s.find("oy",pos3);
// }
// int pos4 = s.find("b");
// while(pos4!=-1)
// {
// s[pos4] = '.';
// cnt_b++;
// pos4 = s.find("b",pos4);
// }
// int pos5 = s.find("o");
// while(pos5!=-1)
// {
// s[pos5] = '.';
// cnt_b++;
// pos5 = s.find("o",pos5);
// }
// int pos6 = s.find("y");
// while(pos6!=-1)
// {
// s[pos6] = '.';
// cnt_b++;
// pos6 = s.find("y",pos6);
// }
// int pos7 = s.find("girl");
// while(pos7!=-1)
// {
// s[pos7] = s[pos7+1] = s[pos7+2] = s[pos7+3] = '.';
// cnt_g++;
// pos7 = s.find("girl",pos7);
// }
// int pos8 = s.find("gir");
// while(pos8!=-1)
// {
// s[pos8] = s[pos8+1] = s[pos8+2] = '.';
// cnt_g++;
// pos8 = s.find("gir",pos8);
// }
// int pos9 = s.find("irl");
// while(pos9!=-1)
// {
// s[pos9] = s[pos9+1] = s[pos9+2] = '.';
// cnt_g++;
// pos9 = s.find("irl",pos9);
// }
// int pos10 = s.find("gi");
// while(pos10!=-1)
// {
// s[pos10] = s[pos10+1] = '.';
// cnt_g++;
// pos10 = s.find("gi",pos10);
// }
// int pos11 = s.find("ir");
// while(pos11!=-1)
// {
// s[pos11] = s[pos11+1] = '.';
// cnt_g++;
// pos11 = s.find("ir",pos11);
// }
// int pos12 = s.find("rl");
// while(pos12!=-1)
// {
// s[pos12] = s[pos12+1] = '.';
// cnt_g++;
// pos12 = s.find("rl",pos12);
// }
// int pos13 = s.find("g");
// while(pos13!=-1)
// {
// s[pos13] = '.';
// cnt_g++;
// pos13 = s.find("g",pos13);
// }
// int pos14 = s.find("i");
// while(pos14!=-1)
// {
// s[pos14] = '.';
// cnt_g++;
// pos14 = s.find("i",pos14);
// }
// int pos15 = s.find("r");
// while(pos15!=-1)
// {
// s[pos15] = '.';
// cnt_g++;
// pos15 = s.find("r",pos15);
// }
// int pos16 = s.find("l");
// while(pos16!=-1)
// {
// s[pos16] = '.';
// cnt_g++;
// pos16 = s.find("l",pos16);
// }
// cout << cnt_b << endl << cnt_g;
// }
#include <bits/stdc++.h>
using namespace std;
int main() {
string s; cin >> s;
int b=0, g=0;
for(int i=0;i<s.size();++i) {
if(s[i]=='b'||s[i+1]=='o'||s[i+2]=='y') b++;
if(s[i]=='g'||s[i+1]=='i'||s[i+2]=='r'||s[i+3]=='l') g++;
}
cout << b << "\n" << g;
}
P1553 数字反转(升级版)
• 分情况处理整数、分数、小数、百分数,注意前导零处理。
代码如下:
#include <bits/stdc++.h>
using namespace std;
string rev(string s) {
reverse(s.begin(),s.end());
size_t p = s.find_first_not_of('0');
return p!=string::npos ? s.substr(p) : "0";
}
int main() {
string s; cin >> s;
if(s.find('.')!=string::npos) {
string a = rev(s.substr(0,s.find('.')));
string b = rev(s.substr(s.find('.')+1));
cout << a << "." << (b.empty()?"0":b);
} else if(s.find('/')!=string::npos) {
cout << rev(s.substr(0,s.find('/'))) << "/" << rev(s.substr(s.find('/')+1));
} else if(s.find('%')!=string::npos) {
cout << rev(s.substr(0,s.size()-1)) << "%";
} else {
cout << rev(s);
}
}
P1603 斯诺登的密码
• 将单词转换为对应数值,取最小值组合,注意前导零处理。
代码如下:
#include <bits/stdc++.h>
using namespace std;
int main() {
map<string,int> mp{
{"one",1},{"two",4},{"three",9},{"four",16},{"five",25},{"six",36},
{"seven",49},{"eight",64},{"nine",81},{"ten",0},{"eleven",21},{"twelve",44},
{"thirteen",69},{"fourteen",96},{"fifteen",25},{"sixteen",56},{"seventeen",89},
{"eighteen",24},{"nineteen",61},{"twenty",0},{"a",1},{"both",4},{"another",1},{"first",1},{"second",4},{"third",9}
};
vector<int> v;
for(int i=0;i<6;++i) {
string s; cin >> s;
if(mp.count(s)) {
int x=mp[s];
v.push_back(x%100);
}
}
if(v.empty()) return cout<<0,0;
sort(v.begin(),v.end());
cout << v[0];
for(size_t i=1;i<v.size();++i)
cout << setw(2) << setfill('0') << v[i];
}
P1200 你的飞碟在这儿
• 计算字母乘积模47比较结果,注意取模运算。
代码如下:
#include <bits/stdc++.h>
using namespace std;
int main() {
string a,b; cin>>a>>b;
auto f=[](string s){
int res=1;
for(char c:s) res=res*(c-'A'+1)%47;
return res;
};
cout << (f(a)==f(b)?"GO":"STAY");
}
P1597 语句解析
• 维护变量当前值,直接解析赋值语句即可。
代码如下:
#include <bits/stdc++.h>
using namespace std;
int main() {
int v[3]={0};
string s; cin>>s;
for(int i=0;i<s.size();i+=5) {
char var = s[i], val = s[i+3];
int x = isalpha(val) ? v[val-'a'] : val-'0';
v[var-'a'] = x;
}
printf("%d %d %d",v[0],v[1],v[2]);
}
P1598 垂直柱状图
• 统计字母频率,逐行输出星号柱状图。
代码如下:
#include <bits/stdc++.h>
using namespace std;
int main() {
int cnt[26]={0}, mx=0;
for(int i=0;i<4;++i) {
string s; getline(cin,s);
for(char c:s) if(isupper(c))
mx = max(mx, ++cnt[c-'A']);
}
for(int h=mx;h>0;--h) {
string line;
for(int i=0;i<26;++i)
line += (cnt[i]>=h ? "* " : " ");
while(!line.empty() && line.back()==' ') line.pop_back();
cout << line << '\n';
}
cout << "A B C D E F G H I J K L M N O P Q R S T U V W X Y Z";
}
更多推荐
所有评论(0)