法雷数列

http://topic.csdn.net/u/20090530/19/912d79b3-f9d0-44d7-8bf5-2dc60be0a197.html

 


考虑在0和1之间的所有分母不大于N的最简分数,下面是N=5时的情况: 0/1,  1/5, 1/4 ,1/3 ,2/5 ,1/2 ,3/5, 2/3, 3/4 ,4/5, 1/1 .总共有11个分数。写出一个程序对于给定的整数N(1 <=N <=100),按从小到大的顺序打印出这些分数。还要打印出它们的总数。在每个分数后面打印出3个空格,使它们在显示的时候一行不会很长。
要求:当N <1或N>100时,程序应判错。
运行举例:
Please input the N?
5
0/1  1/5  1/4  1/3  2/5  1/2  3/5  2/3  3/4  4/5  1/1
There were 11 fractions.

 


这个序列叫法雷序列。


 

Farey Sequence 的构造
法雷数列的构造可采用2分法,即如果 a/b, c/d (a/b <c/d)是一个n级法雷数列中的两个元素,且b+d <=n,  则可以在a/b, c/d 中间插入一个分数 (a+b)/(c+d)。下面以5级法雷数列为例,给出详细的过程。

step1: 准备两个数 0/1, 1/1 作为整个法雷数列的第一个元素和最后一个元素
  0/1, 1/1
step2: 在两个数中间插入1个数1/2, 变为
  0/1, 1/2, 1/1
step3: 在每对相邻两个数中间插入1个数,变为
  0/1, 1/3, 1/2, 2/3, 1/1
step4: 在每对相邻两个数中间插入1个数,变为
  0/1, 1/4, 1/3, 2/5, 1/2, 3/5, 2/3, 3/4, 1/1
step5: 0/1 和 1/4 之间 和3/4和 1/1 仍然可插入1个数,使得插入的数分母不大于5
  0/1, 1/5, 1/4, 1/3, 2/5, 1/2, 3/5, 2/3, 3/4, 4/5, 1/1
至此,该序列包含了所有分母不大于5的最简真分数,且各个分数以递增顺序排列。

以下是将分母小于等于n的不可约真分数按升序排序,并在第一个分数前加0/1,最后一个分数后加1/1 的 C++ 代码实现: ```cpp #include <iostream> #include <vector> #include <algorithm> using namespace std; // 求两个数的最大公约数 int gcd(int a, int b) { if (b == 0) return a; return gcd(b, a % b); } // 判断一个分数是否为不可约真分数 bool isProperFraction(int numerator, int denominator) { int commonDivisor = gcd(numerator, denominator); return commonDivisor == 1 && numerator < denominator; } // 比较两个分数的大小(按升序排序) bool compareFractions(pair<int, int> a, pair<int, int> b) { return a.first * b.second < b.first * a.second; } // 生成n级的法雷序列 vector<pair<int, int>> generateFareySequence(int n) { vector<pair<int, int>> fareySequence; fareySequence.push_back(make_pair(0, 1)); for (int denominator = n; denominator >= 1; denominator--) { for (int numerator = 1; numerator < denominator; numerator++) { if (isProperFraction(numerator, denominator)) { fareySequence.push_back(make_pair(numerator, denominator)); } } } fareySequence.push_back(make_pair(1, 1)); sort(fareySequence.begin(), fareySequence.end(), compareFractions); return fareySequence; } int main() { int n; cout << "请输入自然数n(n<=10): "; cin >> n; vector<pair<int, int>> fareySequence = generateFareySequence(n); for (auto fraction : fareySequence) { cout << fraction.first << "/" << fraction.second << endl; } return 0; } ``` 在上述代码中,我们首先定义了一个 `pair<int, int>` 类型的向量 `fareySequence` 来存储分数。然后,我们使用 `generateFareySequence` 函数生成了 n 级的法雷序列,并将其存储在 `fareySequence` 中。最后,我们按顺序输出法雷序列中的每个分数。 请注意,为了使分数能够按升序排序,我们还定义了一个 `compareFractions` 函数来比较两个分数的大小。在输出法雷序列时,我们使用 `fraction.first` 和 `fraction.second` 分别表示分数的分子和分母。
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值