# 3041. 分数的加减运算

### include

using namespace std;

### define LL long long

int T;

struct fraction
{
LL up,down;
LL gcd(LL aa,LL bb)
{
aa=abs(aa);bb=abs(bb);
if(aa<bb) swap(aa,bb);
if(bb==0) return aa;
else return gcd(bb,aa%bb);
}
void reduction()
{
if(up==0)
{
down=1;
return;
}
LL GCD=gcd(up,down);
up/=GCD;down/=GCD;
return;
}
fraction(LL aa,LL bb=1)
{
up=aa;down=bb;
(*this).reduction();
}
void print()
{
if(down==1) printf(“%lld\n”,up);
else printf(“%lld/%lld\n”,up,down);
}
};

fraction operator+(const fraction& aa,const fraction& bb)
{
fraction ret(aa.upbb.down+bb.upaa.down,aa.down*bb.down);
ret.reduction();
return ret;
}

/fraction operator-(const fraction& aa,const fraction& bb)
{
fraction ret(aa.up
bb.down-bb.upaa.down,aa.downbb.down);
ret.reduction();
return ret;
}*/

void solve()
{
int useless;
cin>>useless;
string line;
cin>>line;

int pos=0,ll=line.length();
fraction ans(0);
while(pos<ll)
{
LL a,b;
int symbol=1;
if(line[pos]==’+’) pos++;
if(line[pos]==’-‘) {symbol=-1;pos++;}
LL num=0;
while(pos<ll && isdigit(line[pos]))
{
num=num10+line[pos]-‘0’;
pos++;
}
a=num
symbol;
pos++;

num=0;
while(pos<ll && isdigit(line[pos]))
{
num=num*10+line[pos]-'0';
pos++;
}
b=num;

fraction(a,b);
ans=ans+fraction(a,b);

}
ans.print();
return;
}

int main()
{
scanf(“%d”,&T);
for(int step=0;step<T;step++)
{
printf(“case #%d:\n”,step);
solve();
}
return 0;
}

#include <stdio.h>
#include <string.h>
#include <stdlib.h>
long long Abs(long long x)//为了用gcd写了个abs……
{
if(x<0) return -x;
else return x;
}
long long gcd(long long a, long long b)
{
if(Abs(a)<Abs(b)) {a^=b; b^=a; a^=b;}
if(b==0) return 1;//分子有可能为0要考虑这种情况
if(a%b) return gcd(b, a%b);
else return b;
}
int main()
{
int T, I;
scanf("%d",&T);
for(I=0; I<T; I++)
{
int n, i, l, cnt=0, sig=1, pos=0;
long long a[30][2], x;
char s[85];
scanf("%d %s",&n,s);
l=strlen(s);
for(i=0; i>n; i++) {a[i][0]=0; a[i][1]=0;}
if(n-1)//分数多于一个
{
for(i=0; i<l;)
{
if(s[i]=='+') {sig=1; pos=0; if(i) cnt++; i++;}
else if(s[i]=='-') {sig=-1; pos=0; if(i) cnt++; i++;}
else if(s[i]=='/') {pos=1; i++;}
else
{
x=s[i++]-'0';
while(s[i]>='0' && s[i]<='9')
{
x*=10;
x+=s[i++]-'0';
}
a[cnt][pos]=x*sig;
sig=1;
}
}
for(i=0; i<cnt; i++)
{
a[i+1][0]*=a[i][1];
a[i][0]*=a[i+1][1];
a[i+1][1]*=a[i][1];
a[i+1][0]+=a[i][0];
x=gcd(a[i+1][0], a[i+1][1]);
a[i+1][0]/=x;
a[i+1][1]/=x;
}
if(a[i][1]<0) {a[i][1]*=-1; a[i][0]*=-1;}//分母有负号
if(a[i][0]==0) printf("case #%d:\n0\n",I);//分子为0
else if(a[i][1]==1) printf("case #%d:\n%lld\n",I,a[i][0]);//分母为1
else printf("case #%d:\n%lld/%lld\n",I,a[i][0],a[i][1]);//一般情况
}
else//只有一个分数
{
for(i=0; i<l; i++) if(s[i]=='/') break;
char m[80];
strncpy(m, s, i);
a[0][0]=(long long)atoi(m);//直接转化为整数
a[0][1]=(long long)atoi(s+i+1);
x=gcd(a[0][0], a[0][1]);
if(a[0][1]<0) {a[0][1]*=-1; a[0][0]*=-1;}//分母有负号
printf("case #%d:\n%lld/%lld\n",I,a[0][0]/x,a[0][1]/x);
}
}
return 0;
}

Hints:相加时不要写的太粗犷，会哇到怀疑人生的！（用了高精度就是另一回事了）QwQ

1.处理输入：可以用简单的scanf(“%d/%d”,&a,&b)，//scanf对于%d是可以处理’+‘号的..
2.计算：两个分数处理得到结果与下一个计算，然后重复上述过程;注意每次得到的分数值都需要”a.约分 b.将符号提到分子”
3.输出：在计算中每次得到的值都完成了提符号和化简。直接查看分母，为1时输出分子，不为1则输出numerator/denominator
4.分数化简代码：

### define longabs(a) (a>0? a : (-a))

typedef struct FRAC
{
long long numr;
long long dnmt;
}frac;
frac myfrac[100];

long long gcd(long long a,long long b)
{
return b?gcd(b,a%b):a;
}
void simple(long long a,long long b)
{
long long aa=a,bb=b;
long long bcf=gcd(aa,bb);
(a)=aa/bcf,(b)=bb/bcf;
}
frac FracSimple(frac in)
{
simple(&in.numr,&in.dnmt);
int tag=1;
if(in.numr==0)tag=0;
else if( (( in.numr/longabs(in.numr)) * (in.dnmt/longabs(in.dnmt))) <0) tag=-1;
return (frac){longabs(in.numr)*tag,longabs(in.dnmt) };
}

### include

using namespace std;
long long int gcd(long long int a,long long int b)
{
if(a%b==0) return b;
else return gcd(b,a%b);
}

void solve()
{
int num;
cin>>num;
char s[81];
long long int a[31];
long long int b[31];
scanf(“%s”,s);
int l=strlen(s);
long long int numup=0;
long long int numdown=0;
long long int suan=0;
long long int gcdn=0;
int sqr=1;
int k=0;
for(int i=0;i=‘0’&&s[i]<=‘9’) suan=suan10+s[i]-‘0’;
if(s[i]==’/’&&suan!=0) {
a[k]=suan
sqr;
suan=0;
sqr=1;
//cout<<i<<ends<<k<<ends<<a[k]<<endl;
}
if(s[i]==’-‘){
sqr=-1;
if(suan!=0)
{b[k]=suan;
//cout<<i<<ends<<k<<ends<<b[k]<<endl;
suan=0;
k++;}

}
if(s[i]=='+'){
if(suan!=0)
{b[k]=suan;
//cout<<i<<ends<<k<<ends<<b[k]<<endl;
suan=0;
k++;}
}
}
if(suan!=0) b[k]=suan;
numup=a[0],numdown=b[0];
//cout<<k<<endl;
//for(int i=0;i<=k;i++) cout<<a[i]<<ends<<b[i]<<endl;
for(int i=1;i<=k;i++)
{
numup=numup*b[i]+numdown*a[i];
numdown=numdown*b[i];
gcdn=gcd(numup,numdown);
numup/=gcdn;
numdown/=gcdn;
}
gcdn=gcd(numup,numdown);
numup/=gcdn;
numdown/=gcdn;
if(numdown<0) numdown*=-1,numup*=-1;
if(numdown==1) cout<<numup<<endl;

else cout<>T;
for(int i=0;i<T;i++)
{
printf(“case #%d:\n”,i);
solve();
}
}