題目鏈接
Description
衆所周知,字符串是不會在區域賽之類的比賽中出現的
但是爲了鍛鍊大家處理字符串的能力
讓大家多一個沒有用處的能力(bushi
給定n個字符串(從1開始編號),每個字符串中的字符位置從0開始編號,1≤length≤500,現有一下幾種操作:
copy N X L :取出第N個字符串中以下標爲X的字符開始的長度爲L的字符串
add S1 S2:判斷S1,S2是否均爲0-99999之間的整數,若是則將其轉化爲整數做加法,否則做字符串加法(即"10"+"1"="101"),返回的值爲一個字符串
find S N:在第N個字符串中從左到右尋找字符串S,若找到,返回其第一次出現的位置,否則返回字符串的長度
rfind S N:在第N個字符串中從右到左尋找字符串S,若找到,返回其第一次出現的位置,否則返回字符串的長度
insert S N X:在第N個字符串的第X個位置後插入字符串S
reset S N:將第N個字符串變爲S
print N:打印輸出第N個字符串
printall:打印輸出所有字符串
over:結束操作
Tips:其中N,X,L可由find和rfind操作表達式構成,S,S1,S2可由copy和add操作表達式構成
Input
第一行爲一個整數n(1≤n≤20)
接下來n行爲n個字符串,字符串中不包含空格及操作命令
接下來若干行爲一系列操作,直到over結束
Output
根據操作輸出對應字符串
這道題很好的反饋了我們對於字符串string的操作的認知還有很大的不足。
介紹幾個基本的string的基本操作
substr(開始下標,結束下標)
提取串的某個子串。返回string類型。
find(字符串)
在串中找第一個出現該字符串的下標位置。返回整型。
rfind(字符串)
與find相同,只是找到最後一個出現的該字符串的下標位置。返回整型。
string::npos
當在字符串中查找(返回類型爲整型時),但是沒有找到時候的情況。
erase(開始下標,結束下標)
刪除串中的某一段。
atoi( char * 類型 )
將字符串(char)類型轉換爲整型。
c_str()
將string類型轉換爲char *類型。
to_string(整型)
將整型轉化爲string類型。
insert(位置(int), 字符串(string) )
在該位置插入一個字符串,字符串位置爲該位置。
然後的話,這道題就有點像正則表達式的做法了,我們可以維護一個棧來實現這樣的基本操作,最好別使用遞歸來做,因爲遞歸不好判斷它的意圖,不如直接從後往前塞。
#include <iostream>
#include <cstdio>
#include <cmath>
#include <string>
#include <cstring>
#include <algorithm>
#include <limits>
#include <vector>
#include <stack>
#include <queue>
#include <set>
#include <map>
#include <bitset>
#include <unordered_map>
#include <unordered_set>
#define lowbit(x) ( x&(-x) )
#define pi 3.141592653589793
#define e 2.718281828459045
#define INF 0x3f3f3f3f
#define HalF (l + r)>>1
#define lsn rt<<1
#define rsn rt<<1|1
#define Lson lsn, l, mid
#define Rson rsn, mid+1, r
#define QL Lson, ql, qr
#define QR Rson, ql, qr
#define myself rt, l, r
using namespace std;
typedef unsigned long long ull;
typedef unsigned int uit;
typedef long long ll;
stack<string> st;
string s[25];
int N;
bool Is_Num(string ch)
{
int len = (int)ch.size();
if(len > 5) return false;
for(int i=0; i<len; i++) if(ch[i] < '0' || ch[i] > '9') return false;
return true;
}
int main()
{
ios::sync_with_stdio(false); cin.tie(nullptr); cout.tie(nullptr);
cin >> N;
for(int i=1; i<=N; i++) cin >> s[i];
string op, SS;
while(getline(cin, op) && op != "over")
{
while(true)
{
if(op.empty()) break;
int beg = (int)op.rfind(" ");
if(beg == string::npos)
{
SS = op;
op.clear();
}
else
{
SS = op.substr(beg + 1, op.size() - 1);
op.erase(beg, op.size() - 1);
}
if(SS.empty()) continue;
if(SS == "copy")
{
int n = atoi(st.top().c_str()); st.pop();
int x = atoi(st.top().c_str()); st.pop();
int l = atoi(st.top().c_str()); st.pop();
string ans = s[n].substr(x, l);
st.push(ans);
}
else if(SS == "add")
{
string S1 = st.top(); st.pop();
string S2 = st.top(); st.pop();
if(Is_Num(S1) && Is_Num(S2)) st.push(to_string(atoi(S1.c_str()) + atoi(S2.c_str())));
else st.push(S1 + S2);
}
else if(SS == "find")
{
string S = st.top(); st.pop();
int n = atoi(st.top().c_str()); st.pop();
int ans = (int)s[n].find(S);
if(ans == string::npos) ans = (int)s[n].size();
st.push(to_string(ans));
}
else if(SS == "rfind")
{
string S = st.top(); st.pop();
int n = atoi(st.top().c_str()); st.pop();
int ans = (int)s[n].rfind(S);
if(ans == string::npos) ans = (int)s[n].size();
st.push(to_string(ans));
}
else if(SS == "insert")
{
string S = st.top(); st.pop();
int n = atoi(st.top().c_str()); st.pop();
int x = atoi(st.top().c_str()); st.pop();
s[n].insert(x, S);
}
else if(SS == "reset")
{
string S = st.top(); st.pop();
int n = atoi(st.top().c_str()); st.pop();
s[n] = S;
}
else if(SS == "print")
{
int n = atoi(st.top().c_str()); st.pop();
cout << s[n] << endl;
}
else if(SS == "printall")
{
for(int i=1; i<=N; i++) cout << s[i] << endl;
}
else st.push(SS);
if(st.empty()) break;
}
}
return 0;
}