关于数论:数论专题BZCD基础上机试题

38次阅读

共计 5778 个字符,预计需要花费 15 分钟才能阅读完成。

BZ: 阶乘的和

有些数能够示意成若干个不同阶乘的和。例如,9=1!+2!+3!。小明对这些数很感兴趣,所以他给你一个正整数 n,想让你通知他这个数是否能够示意成若干个不同阶乘的和。
输出
输出蕴含多组测试数据。每组输出为一个非负整数 n(n<=1000000),当 n 为正数时,输出完结。
输入
对于每组输出,如果 n 能够示意成若干个不同阶乘的和,则输入 YES,否则输入 NO。
样例输出 Copy
9
-1
样例输入 Copy
YES

//http://www.voidcn.com/article/p-pfvdxemp-bqa.html
#include<iostream>
#include<algorithm>
#include<string>
#include<string.h>
using namespace std;
//10 的阶乘等于 362 8800 > 100 0000 ,9! = 362 880 < 1000000
int main(){
    int t = 0;
    int a[10] = {1,1,2,6,24,120,720,5040,40320,362880};// 寄存 0 - 9 各个数字的阶乘 
    while(scanf("%d",&t), t >= 0){if(t == 0){printf("NO\n");
        }else{for(int i = 9; i >= 0; i--){if(t >= a[i]){t -= a[i];// 向越来越小的阶乘循环求证失去的差是否用更小的阶乘示意 
                }
            }
            if(t == 0){// 如果最初做差等于 0,示意刚好被若干个阶乘齐全示意 
                printf("YES\n");
            }else{// 否则不满足条件 
                printf("NO\n");
            }
        } 
    }
    return 0;
}

CA: 大数取模

现给你两个正整数 A 和 B,请你计算 A mod B。
为了使问题简略,保障 B 小于 100000。
输出
输出蕴含多组测试数据。每行输出蕴含两个正整数 A 和 B。A 的长度不超过 1000,并且 0 <B<100000。
输入
对于每一个测试样例,输入 A mod B。
样例输出 Copy
2 3
12 7
152455856554521 3250
样例输入 Copy
2
5
1521

//#include<iostream>
//#include<algorithm>
//#include<cstring>
//#include<cmath>
//using namespace std;
///* 就是对大数的每一位取模,再相加。//  有公式:
//  (a + b) % m = (a % m + b % m) % m; 
// 如:n=1234, 能够合成:  1234=((((0*10)+1)*10+2)*10+3)*10+4 
// 于是对 1234 每一位取模可插入 % 得  1234 % m =(0*10 % m +(n[i] - '0')% m(此处把字符 1 换成数字 1) ) % m = sum
// 持续运算就是 ((sum * 10 % m + n[i] - '0')% m(此处把字符 2 换成数字 2)) % m, 顺次类推.....
//*/
//int main(){//    char a[1005];
//    int b = 0;
//    while(scanf("%s %d",a,&b) != EOF){
//        int sum = 0;
//        for(int i = 0; i < strlen(a); i++){//            sum = (sum * 10 % b + (a[i] - '0') % b) % b;
//        }
//        printf("%d\n",sum);
//    }
//    return 0;
//}

CB: 1 的个数

对于一个给定的 [0,10000] 内的不能被 2 或 5 整除的整数 n,n 放大某些倍数后,后果会是仅由很多 1 组成的一个数 a。当初请你找出最小的那个 a 中蕴含的 1 的个数。
输出
输出蕴含多组测试数据。每组输出为一个整数 n(0<=n<=10000)。
输入
对于每组输出,输入最小的那个 a 中蕴含的 1 的个数。
样例输出 Copy
3
7
9901
样例输入 Copy
3
6
12

//#include<iostream>
//#include<algorithm>
//#include<cstring>
//#include<cmath>
//using namespace std;
///*
// 枚举由 1 组成的数,而后对 n 取模,余数为 0 就是满足条件的数
//(ab)%p = (a%pb)%p 未找到依据
//(a+b)%p = (a%p+b)%p 未找到依据 
//*/
//int main(){//    int n = 0,c;// k 用来记录若干个 1 组成的整数(如 1,11,111....),c 用来记录 k 曾经有几个 1 了 
//    long long k;
//    while(scanf("%d",&n) != EOF){
//        k = 1; 
//        c = 1;
//        while(k < n){
//            k = k * 10 + 1;
//            c++;
//        }
//        while(k % n){// 而 k = k*10 %n +1,则此处 k%n == (k*10 %n +1)%n,由上面(k*10 + 1)%n == (k*10 %n +1)%n 能够看到是对等替换 
//            k = k  * 10 % n + 1;// 此处原本应为(k* 10 + 1)持续枚举,然而数据过大会超限,因为要进行 %n, 故用 (k*10 %n +1) 替换 
//            //(a+b)%p = (a%p+b%p)%p 此处 b 为 1 则 1%p = 1, 故此处 (a+b)%p = (a%p+b)%p,即(k*10 + 1)%n == (k*10 %n +1)%n 
//            c++;
//        }
//        printf("%d\n",c);
//    }
//    return 0;
//}

CC: 丑数

如果一个数的素因子只蕴含 2,3,5 或 7,那么咱们把这种数叫做丑数。序列 1,2,3,4,5,6,7,8,9,10,12,14,15,16,18,20,21,24,25,27… 展现了前 20 个丑数。
请你编程寻找这个序列中的第 n 个元素。
输出
输出蕴含多组测试数据。每组输出为一个整数 n(1<=n<=5842),当 n = 0 时,输出完结。
输入
对于每组输出,输入一行“The nth humble number is number.”。外面的 n 由输出中的 n 值替换,“st”,“nd”,“rd”和“th”这些序数结尾的用法参照输入样例。
样例输出 Copy
1
2
3
4
11
12
13
21
22
23
100
1000
5842
0
样例输入 Copy
The 1st humble number is 1.
The 2nd humble number is 2.
The 3rd humble number is 3.
The 4th humble number is 4.
The 11th humble number is 12.
The 12th humble number is 14.
The 13th humble number is 15.
The 21st humble number is 28.
The 22nd humble number is 30.
The 23rd humble number is 32.
The 100th humble number is 450.
The 1000th humble number is 385875.
The 5842nd humble number is 2000000000.

参考 https://www.nowcoder.com/ques…

//#include<iostream>
//#include<algorithm>
//#include<cstring>
//#include<cmath>
//#include<vector>
//using namespace std;
//int GetUgly(int x);
///*
// 首先从丑数的定义咱们晓得,一个丑数的因子只有 2,3,5,7 
// 那么丑数 p = 2 ^ x * 3 ^ y * 5 ^ z * 7 ^ w; 
// 一个丑数肯定由另一个丑数乘以 2 或者乘以 3 或者乘以 5 或者乘以 7 失去,那么咱们从 1 开始乘以 2,3,5,7
//*/
//int main(){
//    int n = 0;
//    while(scanf("%d",&n) != EOF){//        if(n == 0){
//            break;
//        }
//        if(n % 10 == 1 && n % 100 != 11){// 这里需注意第 11.12.13 的后缀并不是 st.nd.rd 而是 th, 如第十二 twelveth 
//            printf("The %dst humble number is %d.\n",n,GetUgly(n));
//        }else if(n % 10 == 2 && n % 100 != 12){//            printf("The %dnd humble number is %d.\n",n,GetUgly(n));
//        }else if(n % 10 == 3 && n % 100 != 13){//            printf("The %drd humble number is %d.\n",n,GetUgly(n));
//        }else{//            printf("The %dth humble number is %d.\n",n,GetUgly(n));
//        }
//    }
//    return 0;
//}
//int GetUgly(int x){//    if(x < 11){
//        return x;//11 之前的数均为其自身 
//    }
//    vector<int> arr;// 开拓丑数用的动静数组 
//    int t2 = 0, t3 = 0, t5 = 0, t7 = 0,ugnum = 1;// 四个丑数因子队列(2,3,5,7)的数组指针,各队头元素的最小值(ugnum)进入丑数数组 
//    arr.push_back(ugnum);//ugnum 最小的第一个丑数初值为 1,进入数组 
//    while(arr.size() < x){// 当数组的长度 = x - 1(从 0 开始)时,输入第 x 个丑数的值
//        ugnum = min(min(arr[t2] * 2, arr[t3] * 3),min(arr[t5] * 5,arr[t7] * 7));// 选出四个队列头最小的数
//        if(arr[t2] * 2 == ugnum){// 上述最小值所在的队列指针 ++ 
//            t2++;
//        }
//        if(arr[t3] * 3 == ugnum){// 这三个 if 有可能进入一个或者多个,进入多个是三个队列头最小的数有多个的状况(如 6 呈现在 2 和 3 队列头) 
//            t3++;
//        }
//        if(arr[t5] * 5 == ugnum){
//            t5++;
//        } 
//        if(arr[t7] * 7 == ugnum){
//            t7++;
//        } 
//        arr.push_back(ugnum); // 选出的最小丑数入丑数数组 
//    }
//    return ugnum;
//}

上一个是利用 vector 数组来计算,上面是一般 array 数组的版本,能够参考一下

//#include<iostream>
//#include<algorithm>
//#include<cstring>
//#include<cmath>
//#include<vector>
//using namespace std;
//int GetUgly(int x);
///*
// 首先从丑数的定义咱们晓得,一个丑数的因子只有 2,3,5,7 
// 那么丑数 p = 2 ^ x * 3 ^ y * 5 ^ z * 7 ^ w; 
// 一个丑数肯定由另一个丑数乘以 2 或者乘以 3 或者乘以 5 或者乘以 7 失去,那么咱们从 1 开始乘以 2,3,5,7
//*/
//int main(){
//    int n = 0;
//    while(scanf("%d",&n) != EOF){//        if(n == 0){
//            break;
//        }
//        if(n % 10 == 1 && n % 100 != 11){// 这里需注意第 11.12.13 的后缀并不是 st.nd.rd 而是 th, 如第十二 twelveth 
//            printf("The %dst humble number is %d.\n",n,GetUgly(n));
//        }else if(n % 10 == 2 && n % 100 != 12){//            printf("The %dnd humble number is %d.\n",n,GetUgly(n));
//        }else if(n % 10 == 3 && n % 100 != 13){//            printf("The %drd humble number is %d.\n",n,GetUgly(n));
//        }else{//            printf("The %dth humble number is %d.\n",n,GetUgly(n));
//        }
//    }
//    return 0;
//}
//int GetUgly(int x){//    if(x < 11){
//        return x;//11 之前的数均为其自身 
//    }
//    int arr[5850];// 开拓丑数用的动静数组
//    arr[1] = 1; 
//    int t2 = 1, t3 = 1, t5 = 1, t7 = 1,i,j;// 四个丑数因子队列(2,3,5,7)的数组指针,各队头元素的最小值(ugnum)进入丑数数组 
////    arr.push_back(ugnum);//ugnum 最小的第一个丑数初值为 1,进入数组 
//    for(i=2;i<=5842;i++){// 当数组的长度 = x - 1(从 0 开始)时,输入第 x 个丑数的值
//        arr[i] = min(min(arr[t2] * 2, arr[t3] * 3),min(arr[t5] * 5,arr[t7] * 7));// 选出四个队列头最小的数
//        if(arr[t2] * 2 == arr[i]){// 上述最小值所在的队列指针 ++ 
//            t2++;
//        }
//        if(arr[t3] * 3 == arr[i]){// 这三个 if 有可能进入一个或者多个,进入多个是三个队列头最小的数有多个的状况(如 6 呈现在 2 和 3 队列头) 
//            t3++;
//        }
//        if(arr[t5] * 5 == arr[i]){
//            t5++;
//        } 
//        if(arr[t7] * 7 == arr[i]){
//            t7++;
//        } 
////        arr.push_back(ugnum); // 选出的最小丑数入丑数数组
//    }
//    return arr[x];
//}

CD: 阶乘数列

求 Sn=1!+2!+3!+4!+5!+…+n! 之值,其中 n 是一个整数。(1≤n≤10)

输出
n

输入
Sn

样例输出 Copy
5
样例输入 Copy
153

//#include<iostream>
//#include<algorithm>
//#include<cstring>
//#include<cmath>
//using namespace std;
///*
// 
//*/
//int main(){
//    int n = 0,sum = 0,s; 
//    while(scanf("%d",&n) != EOF){//        for(int i = 1; i <= n; i++){
//            s = 1;
//            for(int j = i; j >= 1; j--){
//                s *= j;
//            }
//            sum += s;
//        }
//        printf("%d\n",sum);
//    }
//    return 0;
//}

正文完
 0