2.1.2 Ordered Fractions 顺序的分数
一、题目描述
★Ordered Fractions 顺序的分数
输入一个自然数N
请写一个程序来增序输出分母小于等于N 的既约真分数。即输入一个自然数N,对于一个最简分数a/b(分子和分母互质的分数),满足1<=b<=N,0<=a/b<=1,请找出所有满足条件的分数。
PROGRAM NAME: frac1
INPUT FORMAT
单独的一行 一个自然数N(1..160)
SAMPLE INPUT (file frac1.in)
5
OUTPUT FORMAT
每个分数单独占一行
SAMPLE OUTPUT (file frac1.out)
0/1
1/5
1/4
1/3
2/5
1/2
3/5
2/3
3/4
4/5
1/1
二、解题思路
这个题目十分简单,直接枚举所有的真分数,在进行排序。
1、枚举所有真分数,
for(i=1;i<=N;i++)//分子
for(j=i+1;j<=N;j++)//分母大于分子
{
if (gcd(i,j)==1) //求两者的最大公约数,判断是否为1(分子分母互质),即不可约的分数。
{ Fract[k].nmt=i;
Fract[k].dnmt=j;
k++;
}
}
2、优化
1)0/1,1/x不能漏了!有1/1
2)若是两个偶数,不用判断绝对不行
3)两个分数比较大小,只需交叉相乘即可,无需另开data储存具体值。
相关代码:
#include <iostream>
#include <cstdio>
#include <algorithm>
using namespace std;
int N;
int st[12300];//
int gcd(int a,int b){
return b==0 ? a:gcd(b,a%b);
}
typedef struct fract fract;
struct fract{
int nmt; //numerator 分子 要求真分数;
int dnmt; //denominator 分母
};
fract Fract[12300]; //12880
int cmp(int a,int b)
{
return (Fract[a].nmt*Fract[b].dnmt<Fract[b].nmt*Fract[a].dnmt)? 1:0;
}
int main()
{
freopen("frac1.in","r",stdin);
freopen("frac1.out","w",stdout);
cin>>N;
int i,j,k=0;
Fract[0].nmt=0,Fract[0].dnmt=1;k=k+1;
for(i=1;i<=N;i++)
for(j=i+1;j<=N;j++)
{
if (gcd(i,j)==1)
{ Fract[k].nmt=i;
Fract[k].dnmt=j;
k++;
}
}
Fract[k].nmt=1,Fract[k].dnmt=1,k=k+1;
for (i=0;i<k;i++)
{
st[i]=i;
}
sort(st,st+k,cmp);
for (i=0;i<k;i++)
{
cout<<Fract[st[i]].nmt<<"/"<<Fract[st[i]].dnmt<<endl;
}
return 0;
}