代码来自:P1080 [NOIP2012 提高组] 国王游戏
输入样例:
3
1 1
2 3
7 4
4 6
输出
2
见代码int main()部分注释 code:
#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
const int MAXN=1e5;
const int siz=8;
const long long MOD=1e8;//1e siz压位需要取的模数
char ch1[MAXN],ch2[MAXN];
bool f1,f2,f;
long long n;
long long a[MAXN>>2],b[MAXN>>2],s[MAXN>>2];
long long cp[MAXN>>2],lt[MAXN>>2],wsd[MAXN>>2];
string write(long long num[]);//输出函数
void clear(long long num[]);//重置函数
void ry(long long num[]);//>>二进制右移
void ly(long long num[]);//<<二进制左移
void cpy(long long num1[],long long num2[]);//复制函数
int cmp(long long num1[],long long num2[]);//比较函数
void pls(long long a[],long long b[]);//plus加法运算
void mnu(long long a[],long long b[]);//minus减法运算
void mul(long long a[],long long b[]);//multiply乘法运算
void div(long long a[],long long b[]);//divided除法运算
string write(long long num[]){
string ans="";
if(f) putchar('-'),f=0;
ans+=to_string(num[num[0]]);
for(int i=num[0]-1;i;--i)ans+=to_string(num[i]);
return ans;
}
void clear(long long num[]){
for(int i=num[0];i;--i) num[i]=0;
num[0]=1;
}
void ry(long long num[]){
for(int i=num[0];i;--i){
if((num[i]&1)&&i>1) num[i-1]+=MOD;
num[i]>>=1;
}if(!num[num[0]]&&num[0]>1) --num[0];
}
void ly(long long num[]){
++num[0];
for(int i=1;i<=num[0];++i){
num[i]<<=1;
if(num[i-1]>=MOD) num[i-1]-=MOD,++num[i];
}if(!num[num[0]]&&num[0]>1) --num[0];
return;
}
void cpy(long long num1[],long long num2[]){
for(int i=num1[0];i>num2[0];--i) num1[i]=0;
for(int i=0;i<=num2[0];++i) num1[i]=num2[i];
}
int cmp(long long num1[],long long num2[]){
if(num1[0]>num2[0]) return 1;
if(num1[0]<num2[0]) return -1;
for(int i=num1[0];i;--i){
if(num1[i]>num2[i]) return 1;
if(num1[i]<num2[i]) return -1;
}return 0;
}
void init(){
if(ch1[0]=='-') ch1[0]='0',f1=1;
if(ch2[0]=='-') ch2[0]='0',f2=1;//对符号的处理
int l1=strlen(ch1),l2=strlen(ch2);
for(int i=l1-1;i>=0;i-=siz){
long long pw=1;++a[0];
for(int j=i;j>i-siz&&j>=0;--j){
a[a[0]]+=(ch1[j]^48)*pw;
pw=(pw<<3)+(pw<<1);
}
}for(int i=l2-1;i>=0;i-=siz){
long long pw=1;++b[0];
for(int j=i;j>i-siz&&j>=0;--j){
b[b[0]]+=(ch2[j]^48)*pw;
pw=(pw<<3)+(pw<<1);
}
}return;
}
void pls(long long a[],long long b[]){
if(f1^f2){
if(f1) f1^=1,mnu(b,a),f1^=1;
if(f2) f2^=1,mnu(a,b),f2^=1;//加负数等效于减正数
return;
}if(f1&f2){
f1=f2=0,f^=1,pls(a,b);
f1=f2=1;return;
}clear(s);s[0]=max(a[0],b[0])+1;
for(int i=1;i<=s[0];++i){
s[i]+=a[i]+b[i];
if(s[i]>=MOD) s[i]-=MOD,++s[i+1];
}if(!s[s[0]]&&s[0]>1) --s[0];
return;
}
void mnu(long long a[],long long b[]){
if(f1^f2){
if(f1) f1^=1,f^=1,pls(a,b),f1^=1;
if(f2) f2^=1,pls(a,b),f2^=1;//减负数等效于加正数
return;
}if(f1&f2){
f1=f2=0,mnu(b,a);
f1=f2=1;return;
}if(cmp(a,b)==-1){
f^=1;mnu(b,a);return;
}clear(s);s[0]=max(a[0],b[0]);
for(int i=1;i<=s[0];++i){
s[i]+=a[i]-b[i];
if(s[i]<0) s[i]+=MOD,--s[i+1];
}while(!s[s[0]]&&s[0]>1) --s[0];
return;
}
void mul(long long a[],long long b[]){
if(f1^f2) f^=1;
clear(s);s[0]=a[0]+b[0];
for(int i=1;i<=a[0];++i){
for(int j=1;j<=b[0];++j){
s[i+j-1]+=a[i]*b[j];
if(s[i+j-1]>=MOD) s[i+j]+=s[i+j-1]/MOD,s[i+j-1]%=MOD;
}
}if(!s[s[0]]&&s[0]>1) --s[0];
return;
}
void div(long long a[],long long b[]){
if(f1^f2){
if(f1) f1^=1,f^=1,div(a,b),f1^=1;
if(f2) f2^=1,f^=1,div(a,b),f2^=1;
return;
}clear(s);
clear(cp),cp[1]=1;clear(lt);
while(cmp(a,b)!=-1) ly(b),ly(cp);//这里试探商的二进制最高位
while(cp[0]>1||cp[1]){
if(cmp(a,b)!=-1){
mnu(a,b),cpy(a,s);
pls(lt,cp),cpy(lt,s);//倍增减法,算法主体
}ry(b),ry(cp);
}cpy(s,lt),cpy(lt,a);//s为商,lt为余数
return;
}
string chengfa(string a_,string b_){
for(int i=0;i<a_.length();i++)ch1[i]=a_[i];
for(int i=0;i<b_.length();i++)ch2[i]=b_[i];
ch1[a_.length()]='\0';ch2[b_.length()]='\0';
init();clear(s);mul(a,b);
return write(s);
}
string chufa(string a_,string b_){
for(int i=0;i<a_.length();i++)ch1[i]=a_[i];
for(int i=0;i<b_.length();i++)ch2[i]=b_[i];
ch1[a_.length()]='\0';ch2[b_.length()]='\0';
init();clear(s);div(a,b);
return write(s);
}
string _max(string _a,string _b){
if(_a.length()>_b.length())return _a;
if(_b.length()>_a.length())return _b;
for(int i=0;i<_a.length();i++)if(_a[i]-'0'>_b[i]-'0')return _a;else if(_a[i]-'0'<_b[i]-'0')return _b;
return _a;
}
struct _z{
long long _l,_r;
};
bool _cmp(_z _a,_z _b){
return _a._l*_a._r<_b._l*_b._r;
}
string _sum,_ans="0";_z _a[100000000];int _n,_l,_r;
signed main(){
cin>>_n>>_l>>_r;
for(int i=0;i<_n;i++)cin>>_a[i]._l>>_a[i]._r;
sort(_a,_a+_n,_cmp);
cout<<"1 1\n";for(int i=0;i<_n;i++)cout<<_a[i]._l<<" "<<_a[i]._r<<endl;
_sum=to_string(_l);
for(int i=0;i<_n;i++){
_ans=_max(_ans,chufa(_sum,to_string(_a[i]._r)));
cout<<_sum<<" "<<to_string(_a[i]._l)<<endl;//两个乘数相乘 但输出正确运算错误
_sum=chengfa(_sum,to_string(_a[i]._l));
}
cout<<_ans;
return 0;
}
但是若int main()改成这样
int main(){
cout<<chengfa("1","2");
return 0;
}
那么
