洛谷[P1482]Cantor表(升级版)

题目传送门OvO


题目描述

现代数学的著名证明之一是Georg Cantor证明了有理数是可枚举的。他是用下面这一张表来证明这一命题的:

1/1 1/2 1/3 1/4 1/5 …

2/1 2/2 2/3 2/4 …

3/1 3/2 3/3 …

4/1 4/2 …

5/1 …

… 这次与NOIp1999第一题不同的是:这次需输入两个分数(不一定是最简分数),算出这两个分数的积(注意该约分的要约分)后输出积在原表的第几列第几行(若积是整数或1/积,则以“积/1”或“1/积”结算)。

输入输出格式

输入格式:

共两行。每行输入一个分数(不一定是最简分数)。

输出格式:

两个整数,表示输入的两个分数的积在表中的第几列第几行,注意该约分的要约分。


先喷一下这题太水了,,,


首先,你要知道:
约分后的分母是行,分子是列。
于是问题来了:
怎么约分?
很简单:用辗转相除法求最大公约数,然后约分。
然后输出。
完事。

#include//包含所有头文件的头文件
using namespace std;//为了用流,写它
int gcd(int a,int b){
     //辗转相除法求最大公约数
    if (!b)return a;//如果b==0,a是最大公约数
    else return gcd(b,a%b);//不然继续
}
int main(){
     
    ios::sync_with_stdio(false);//流优化
    int a,b,c,d,t;
    char hh;//这家伙对付‘/’号
    cin>>a>>hh>>b>>c>>hh>>d;//读入,不解释
    a*=c;b*=d;//乘一下
    t=gcd(a,b);//求最大公约数
    a/=t,b/=t;//约分
    cout<<b<<" "<<a;//输出
    return 0;//庄严地结束
}

传说中的80行代码:

#include
#include
using namespace std;
enum mode{
     upper=0,lower=1};
class Fraction
{
     
    private:
        int fz;
        int fm;
    public:
        Fraction();
        Fraction(int Fz,int Fm);
        ~Fraction();
        int showfrac(mode mde);
        void get_gcd();
        Fraction operator*(Fraction frac1);
};

Fraction::Fraction()
{
     
    fz=1;
    fm=1;
}

Fraction::Fraction(int Fz,int Fm)
{
     
    if(Fm==0)
        cerr<<"Error : Divided By Zero .\n";
    else
    {
     
        fz=Fz;
        fm=Fm;
    }
}

Fraction::~Fraction()
{
     
}

int Fraction::showfrac(mode mde)
{
     
    if(mde==0)
        return this->fz;
    else
        return this->fm;
}

void Fraction::get_gcd()
{
     
    int cp1=fz,cp2=fm;
    while(cp1!=0 && cp2!=0)
    {
     
        if(cp1>cp2)
            cp1%=cp2;
        else
            cp2%=cp1;
    }
    int gcd=cp1+cp2;
    fz/=gcd;
    fm/=gcd;
}

Fraction Fraction::operator*(Fraction frac1)
{
     
    Fraction answer(fz*frac1.showfrac(upper),frac1.showfrac(lower)*fm);
    answer.get_gcd();
    return answer;
}

int main()
{
     
    int a,b;
    scanf("%d/%d",&a,&b);
    Fraction f1(a,b);
    scanf("%d/%d",&a,&b);
    Fraction f2(a,b);
    Fraction f_ans=f1*f2;
    cout<<f_ans.showfrac(lower)<<" "<<f_ans.showfrac(upper)<<endl;
    return 0;
}

Pascal还是来一个吧:

var
    a,b,c,d:longint;
    s:string[11];//分子分母共10位,分数线1位
function gcd(x,y:longint):longint;//也可以用递归的方式写
var
    r,t:longint;
begin
    if x<y then begin t:=x; x:=y; y:=t; end;//以免出现x
    r:=x mod y;
    while r<>0 do
    begin
        x:=y; y:=r;
        r:=x mod y;
    end;//辗转相除
    exit(y);
end;
begin
    readln(s);
    val(copy(s,1,pos('/',s)-1),a);
    val(copy(s,pos('/',s)+1,9),b);//处理
    readln(s);
    val(copy(s,1,pos('/',s)-1),c); a:=a*c;
    val(copy(s,pos('/',s)+1,9),d); b:=b*d;//同上
    writeln(b div gcd(a,b),' ',a div gcd(a,b));
end.

你可能感兴趣的:(题解,洛谷,OI,P1482,题解)