蓝桥杯—基础训练
数列排序
第二行包含n个整数,为待排序的数,每个整数的绝对值小于10000。
8 3 6 4 9
代码
#include <stdio.h> int main() { int n,x[200],i; //静态数组,分配好空间 scanf("%d",&n); //输入数据 for(i=0;i<n;i++) { scanf("%d",&x[i]); } int temp,flag=1; //flag=1,表示还未完全排好序,仍需继续while;flag=0时,表示已经排好序,直接跳出输出即可 int j=n-1; while(flag) { flag=0; //每次循环将最大的数放到最后合适的位置 for(i=1;i<=j;i++) { if(x[i-1]>x[i]) { temp = x[i-1]; x[i-1]=x[i]; x[i]=temp; flag=1; } } j--;//j表示每次循环将最大的一个数归位后,下一次循环不用再去比较 } //输出排序后的 for(i=0;i<n;i++) { printf("%d\t",x[i]); } printf("\n"); system("pause"); return 0; }
方法2:
动态分配数组:
用到了calloc函数:
- nitems -- 要被分配的元素个数。
- size -- 元素的大小。
#include <stdio.h> #include <stdlib.h> /* run this program using the console pauser or add your own getch, system("pause") or input loop */ //冒泡排序 ,从小到大 void bubbling(int *nums,int n) { int i,j,temp; // n个元素的数组进行 n-1 轮比较。 for(i=0;i<n;i++) { for(j=0;j<n-i-1;j++) { if(nums[j]>nums[j+1]) { temp=nums[j]; nums[j]=nums[j+1]; nums[j+1]=temp; } } } //输出排序好的 for(i=0;i<n;i++) { printf("%d\t",nums[i]); } } int main(int argc, char *argv[]) { int n,*num,i; scanf("%d",&n); //输入n个整数存在数组num中 num=(int*)calloc(n,sizeof(int)); //动态分配数组空间 for(i=0;i<n;i++) { scanf("%d",&num[i]); } bubbling(num,n); free(num); return 0; }
十六进制转八进制
问题描述
给定n个十六进制正整数,输出它们对应的八进制数。
输入格式
输入的第一行为一个正整数n (1<=n<=10)。
接下来n行,每行一个由0~9、大写字母A~F组成的字符串,表示要转换的十六进制正整数,每个十六进制数长度不超过100000。
输出格式
输出n行,每行为输入对应的八进制正整数。
【注意】
输入的十六进制数不会有前导0,比如012A。
输出的八进制数也不能有前导0。
【提示】
先将十六进制数转换成某进制数,再由某进制数转换成八进制。
样例输入
2
39
123ABC
样例输出
71
4435274
代码
方法1:
直接转成八进制,不通过,因为,这里十六进制的数可能很长,已经不能用十进制的方法求解,所以我们选择将十六进制转化为二进制,再转化为八进制
#include <stdio.h> #include <stdlib.h> #include <math.h> void sixteenToeight(int num) { int sum=0,i=0,a; //十进制转八进制:除8取余法 /* 1、取模,记录模值 a0 2、除,记录商 3、用商再次循环,直到商为0 4、输出:an...a0 */ while(num) { a=num%8; num=num/8; sum+=a*pow(10,i); i++; } printf("%d\t",sum); } int main(int argc, char *argv[]) { int n,*num,i,tmp;//tmp为临时变量 scanf("%d",&n); num=(int*)calloc(n,sizeof(int));//动态数组保存输入的十六进制数 //输入 for(i=0;i<n;i++) { scanf("%X",&num[i]); } //转八进制 for(i=0;i<n;i++) { sixteenToeight(num[i]); } return 0; }
方法2:
将十六进制转化为二进制,再转化为八进制
#include<stdio.h> #include<string.h> #define MAX_N 10 // 限定个数,不能超过20个 #define MAX_L 100000 //限定十六进制的长度,不能超过100000 #define MAX_D 400000 int bin[MAX_D]; //存储二进制,每4个存一个二进制 int oct[MAX_D]; //八进制 void Print(int O[],int n) { int i; for(i = n-1;i >= 0;i--) { printf("%d",O[i]); } printf("\n"); } //二进制转化为八进制,并且首位不能为0 int Oct(int l) { int i, j = 0; for(i = l*4-3;i >= 0;i-=3) { if(i == 0 && !(bin[i]*4 + bin[i+1]*2 + bin[i+2])) break; oct[j++] = bin[i]*4 + bin[i+1]*2 + bin[i+2]; } if(i == -2){ if(bin[0]) oct[j++] = bin[0]; } else if(i == -1) { if(bin[0]*2 + bin[1]) oct[j++] = bin[0]*2 + bin[1]; } return j; } //十进制转化为二进制 void dexToBin(int num,int n) { int i; for(i = 3;i >= 0;i--){ bin[n*4+i] = num % 2; num /= 2; } } //十六进制转化为十进制 int Dec(char ch){ if(ch >= '0' && ch <= '9') return ch - '0'; switch(ch) { case 'A': return 10; case 'B': return 11; case 'C': return 12; case 'D': return 13; case 'E': return 14; case 'F': return 15; } return -1; } //十六进制转化为八进制 void dexToOct(char s[]) { int i; //十六进制转化为二进制 for(i = 0;i < (int)strlen(s);i++) { dexToBin(Dec(s[i]),i); //十六进制转化为十进制,十进制转化为二进制 } int n = Oct(strlen(s)); //二进制转化为八进制 Print(oct,n); //打印 } int main() { char s[MAX_N][MAX_L];//二维数组,存于输入的字符串(十六进制) int n,i; scanf("%d",&n); for(i = 0;i < n;i++) scanf("%s",s[i]); for(i = 0;i < n;i++) { dexToOct(s[i]); //十六进制转化为八进制 } }
十六进制转十进制
注:十六进制数中的10~15分别用大写的英文字母A、B、C、D、E、F表示。
代码
最初用int ,会报错,就改为long long int,就可以了
#include <stdio.h> #include <stdlib.h> /* run this program using the console pauser or add your own getch, system("pause") or input loop */ int main(int argc, char *argv[]) { long long int n; scanf("%llX",&n); printf("%lld",n); return 0; }
十进制转十六进制
给出一个非负整数,将它表示成十六进制的形式。
代码
#include <stdio.h> #include <stdlib.h> /* run this program using the console pauser or add your own getch, system("pause") or input loop */ int main(int argc, char *argv[]) { long long int n; scanf("%lld",&n); printf("%llX",n); return 0; }
序列求和
说明:请注意这里的数据规模。
本题直接的想法是直接使用一个循环来累加,然而,当数据规模很大时,这种“暴力”的方法往往会导致超时。此时你需要想想其他方法。你可以试一试,如果使用1000000000作为你的程序的输入,你的程序是不是能在规定的上面规定的时限内运行出来。
本题另一个要值得注意的地方是答案的大小不在你的语言默认的整型(int)范围内,如果使用整型来保存结果,会导致结果错误。
如果你使用C++或C语言而且准备使用printf输出结果,则你的格式字符串应该写成%I64d以输出long long类型的整数。
代码
#include<stdio.h> int main() { long long int n; scanf("%I64d",&n); //(n+1)在前,先运算 printf("%I64d",(n+1)*n/2); //指定字段宽度64输出长整型数据 return 0; }
圆的面积
代码
#include<stdio.h> #define PI 3.14159265358979323 int main() { int r; scanf("%d",&r); //.7f,保证小数位后7位 printf("%.7f",r*r*PI); system("pause"); return 0; }
Fibonacci数列
Fibonacci数列的递推公式为:Fn=Fn-1+Fn-2,其中F1=F2=1。
当n比较大时,Fn也非常大,现在我们想知道,Fn除以10007的余数是多少。
代码
#include<stdio.h> int f(int n) { return (n<3)? 1 : (f(n-1)+f(n-2))%10007; } int main() { int n; scanf("%d",&n); printf("%d",f(n)); system("pause"); return 0; }
#include<stdio.h> int f(int n) { int sum=1,b=1,t,i; for(i=3;i<=n;i++) { t=sum; sum=(sum+b)%10007; //每求一次,要mod一下 b=t; } return sum%10007; //最后将结果也mod } int main() { int n; scanf("%d",&n); printf("%d",f(n)); system("pause"); return 0; }
闰年判断
给定一个年份,判断这一年是不是闰年。
当以下情况之一满足时,这一年是闰年:
1. 年份是4的倍数而不是100的倍数;
2. 年份是400的倍数。
其他的年份都不是闰年。
代码
#include<stdio.h> int f(int n) { if((n%4==0)&&(n%100!=0)|n%400==0) { return 1; } return 0; } int main() { int n; scanf("%d",&n); if(f(n)==1) { printf("yes"); }else { printf("no"); } system("pause"); return 0; }
01字串
对于长度为5位的一个01串,每一位都可能是0或1,一共有32种可能。它们的前几个是:
00000
00001
00010
00011
00100
请按从小到大的顺序输出这32种01串。
代码
#include<stdio.h> void f(int n) { int i; for(i=4;i>=0;i--) { printf("%d",(n>>i)&1); //逐步与1做与运算 } } int main() { int i; for(i=0;i<32;i++) { f(i); printf("\n"); } system("pause"); return 0; }
字母图形
利用字母可以组成一些美丽的图形,下面给出了一个例子:
ABCDEFG
BABCDEF
CBABCDE
DCBABCD
EDCBABC
这是一个5行7列的图形,请找出这个图形的规律,并输出一个n行m列的图形。
BABCDEF
CBABCDE
DCBABCD
EDCBABC
代码
#include<stdio.h> void f(int n,int m) { int i,j; char a[30]={')','A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z'}; char b[28][28]; //b,第0行,0列为空,不用 //b填充第1行 for(i=1;i<=m;i++) { b[1][i]=a[i]; } //b填充第1列 for(i=1;i<=n;i++) { b[i][1]=a[i]; } //将剩下的按行填充 for(i=2;i<=n;i++) { //从2-n行开始,按行填充;从2-m列 ,按列填充 for(j=2;j<=m;j++) { b[i][j]=b[i-1][j-1]; } } for(i=1;i<=n;i++) { for(j=1;j<=m;j++) { printf("%c",b[i][j]); } printf("\n"); } } int main() { int n,m; scanf("%d %d",&n,&m); f(n,m); system("pause"); return 0; }
数列特征
给出n个数,找出这n个数的最大值,最小值,和。
第一行为整数n,表示数的个数。
第二行有n个数,为给定的n个数,每个数的绝对值都小于10000。
1 3 -2 4 5
-2
11
代码
#include<stdio.h> int main(){ int n,*a,i,max,min,sum=0; scanf("%d",&n); a=(int*)calloc(n,sizeof(int)); for(i=0;i<n;i++){ scanf("%d",&a[i]); sum+=a[i]; } max=a[0]; min=a[0]; for(i=1;i<n;i++){ if(a[i]>max){ max=a[i]; } if(a[i]<min){ min=a[i]; } } printf("%d\n%d\n%d\n",max,min,sum); free(a); return 0; }
查找整数
给出一个包含n个整数的数列,问整数a在数列中的第一次出现是第几个。
第一行包含一个整数n。
第二行包含n个非负整数,为给定的数列,数列中的每个数都不大于10000。
第三行包含一个整数a,为待查找的数。
1 9 4 8 3 9
9
代码
#include<stdio.h> int main(){ int n,*Num,i,a,result; scanf("%d",&n); Num=(int*)calloc(n,sizeof(int)); for(i=0;i<n;i++){ scanf("%d",&Num[i]); } scanf("%d",&a); for(i=0;i<n;i++) { if(a==Num[i]) { result=i+1; break; } else { result=-1; } } printf("%d",result); free(Num); return 0; }
杨辉三角形
它的一个重要性质是:三角形中的每个数字等于它两肩上的数字相加。
下面给出了杨辉三角形的前4行:
1
1 1
1 2 1
1 3 3 1
给出n,输出它的前n行。
输入包含一个数n。
1 1
1 2 1
1 3 3 1
代码
#include<stdio.h> int main(){ int n,Num[34][34],i,j; scanf("%d",&n); for(i=0;i<n;i++) { Num[i][0]=1; Num[i][i]=1; } for(i=2;i<n;i++) { for(j=1;j<i;j++) { Num[i][j]=Num[i-1][j]+Num[i-1][j-1]; } } for(i=0;i<n;i++) { for(j=0;j<=i;j++) { printf("%d ",Num[i][j]); } printf("\n"); } return 0; }
特殊的数字
代码
#include <stdio.h> #include <stdlib.h> /* run this program using the console pauser or add your own getch, system("pause") or input loop */ int main(int argc, char *argv[]) { int i,a,b,c; for(i=100;i<1000;i++) { //tmp=i; a=i/100; //a是百位数 b=(i%100)/10;//b是十位数 c=(i%100)%10;//c是个位数 if(a*a*a+b*b*b+c*c*c==i) { printf("%d\n",i); } } return 0; }
回文数
代码
#include <stdio.h> #include <stdlib.h> /* run this program using the console pauser or add your own getch, system("pause") or input loop */ int main(int argc, char *argv[]) { int i,a,b,c,d; for(i=1000;i<10000;i++) { //tmp=i; a=i/1000; //a是千位数 b=i%1000/100;//b是百位数 c=i%1000%100/10;//c是十位数 d=i%1000%100%10;//d是个位数 if(a==d && b==c) { printf("%d\n",i); } } return 0; }
特殊回文数
输入一个正整数n, 编程求所有这样的五位和六位十进制数,满足各位数字之和等于n 。
989989
998899
代码
#include <stdio.h> #include <stdlib.h> /* run this program using the console pauser or add your own getch, system("pause") or input loop */ int main(int argc, char *argv[]) { int i,a,b,c,d,e,f,n,tmp; scanf("%d",&n); for(i=10000;i<1000000;i++) { //tmp=i; tmp=i/10000; //a是万位数 //六位数 if(tmp>9) { a=i/100000; //a是十万数 b=i%100000/10000;//b是万位数 c=i%100000%10000/1000;//c是千位数 d=i%100000%10000%1000/100;//d是百位数 e=i%100000%10000%1000%100/10;//e是十位数 f=i%100000%10000%1000%100%10;//f是个位数 if(a==f && b==e && c==d && (a+b+c+d+e+f==n)) { printf("%d\n",i); } } else { b=i/10000; //b是万位数 c=i%10000/1000; //c是千位数 d=i%10000%1000/100; //d是百位数 e=i%10000%1000%100/10; //e是十位数 f=i%10000%1000%100%10; //f是十位数 if(b==f && c==e && (b+c+d+e+f==n)) { printf("%d\n",i); } } } return 0; }