蓝桥杯常用字符串函数
-
int 转 string
void i2s(int n, string &str){
stringstream stream;
stream <<n;
stream>>str;
}
-
比较字符串大小
int cmp(string a, string b){//比较字符串大小
if(a.find_first_not_of('0') == string::npos) a = '0';
else a.substr(a.find_first_not_of('0'));
if(b.find_first_not_of('0') == string::npos) b = '0';
else b.substr(b.find_first_not_of('0'));
if(a.length() > b.length()) return 1;
else if(a.length() < b.length()) return -1;
else{
if(a > b) return 1;
if(a < b) return -1;
else return 0;
}
}
-
大整数加法
string add(string a,string b){
a = a.substr(a.find_first_not_of('0'));
b = b.substr(b.find_first_not_of('0'));//去掉前缀0
long long lenA = a.length();
long long lenB = b.length();
long long len = max(lenA,lenB) + 10;
//翻转,便于从低位逐步求和
reverse(a.begin(), a.end());
reverse(b.begin(), b.end());
string ans(len,'0');//将答案初始化为00000000...
//将a拷贝到ans中
for(int i = 0; i < lenA; i++){
ans[i] = a[i];
}
//开始执行加法了
int temp = 0;//temp 是上一位相加的进位
for(int i = 0; i < len; ++i){
if(i < b.length())
temp += (ans[i] - '0') + (b[i] - '0'); //一位的加法
else
temp += (ans[i] - '0');
ans[i] = temp % 10 + '0'; //使数字又变回字符形式
temp /= 10;
}
//相加完之后翻转
reverse(ans.begin(),ans.end());
return ans.substr(ans.find_first_not_of('0'));
}
-
大整数减法
string subtract(string a,string b){//大数减法
//完整的减法中,a 可以小于b,这时结果为负数,交换ab即可
//1.翻转
reverse(a.begin(), a.end());
reverse(b.begin(), b.end());
//2.按位减法
//拷贝a到ans中
//string ans = a;
//这里写成了a.length()的话会出大麻烦
for(int i = 0; i < b.length(); i++){
if(a[i] >= b[i]){
a[i] = a[i] - b[i] + '0';//这一位上a>b
}else{ //这一位小了,要借位
int next = 1;
while(a[i + next] == '0') {
a[i+next] = '9';
next++;
}
//这里保证i + k这一位不是0,因为已经跳出了while循环
a[i+next] = a[i+next] - '1' + '0'; //重点语句,必须加上'0' ,这是借位
a[i] = (a[i]-'0'+10) - (b[i]-'0')+ '0'; //10是借位过来的,最后的+'0'使得重新成为了string
}
}
reverse(a.begin(), a.end());
if(a.find_first_not_of('0') == string::npos) return "0";//ans.find_first_not_of('0')有个特殊规则,本身是0的话,总不能把自己去掉
return a.substr(a.find_first_not_of('0'));
}
-
大整数乘法
std::string multiply(std::string a, std::string b){//大数乘法
std::string result = "";
int row = b.size();
int col = a.size() + 1;
int tmp[row][col];
memset(tmp,0, sizeof(int)*row*col);
reverse(a.begin(),a.end());
reverse(b.begin(),b.end());
for(int i = 0; i < b.size(); i++){
for(int j = 0; j < a.size(); j++){
std::string bit_a = std::string(1, a.at(j));
std::string bit_b = std::string(1, b.at(i));
tmp[i][j] += std::stoi(bit_a) * std::stoi(bit_b);
tmp[i][j+1] = tmp[i][j] / 10;
tmp[i][j] %= 10;
}
}
int N = a.size() + b.size();
int sum[N];
memset(sum, 0, sizeof(int)*N);
for(int n = 0; n < N; n++){
int i = 0;
int j = n;
while (i <= n && j >= 0 ){
if(i < row && j < col){
sum[n] += tmp[i][j];
}
i++;
j--;
}
if( n+1 < N ){
sum[n+1] = sum[n] / 10;
sum[n] %= 10;
}
}
bool zeroStartFlag = true;
for (int i = N-1; i >= 0; i--){
if(sum[i]==0 && zeroStartFlag){
continue;
}
zeroStartFlag = false;
result.append(std::to_string(sum[i]));
}
return result;
}
-
大数除法
//除法的本质是减法 ,默认a < b
string divide(string a,string b){//大数除法
string ans = "0.";
for(int i = 0; i < 101; i++){
a.append("0");
int t = 0;
while(cmp(a,b) >= 0){ //a在append("0")之后 >= b 比如 1 / 2就是 (10 / 2) / 10, 10 / 2这时就变成减法
a = subtract(a,b);
t++;
}
string t_str;
i2s(t, t_str); //t是int,t_str是t的字符串形式
ans.append(t_str);
}
return ans;
}