每日10题5
2080: [蓝桥杯][基础练习]十六进制转八进制
题目描述
给定n个十六进制正整数,输出它们对应的八进制数。
输入
输入的第一行为一个正整数n (1<=n<=10)。
接下来n行,每行一个由09、大写字母AF组成的字符串,表示要转换的十六进制正整数,每个十六进制数长度不超过100000。
输出
输出n行,每行为输入对应的八进制正整数。
【注意】
输入的十六进制数不会有前导0,比如012A。
输出的八进制数也不能有前导0。
样例输入
2
39
123ABC
样例输出
71
4435274
提示
- 先将十六进制数转换成某进制数,再由某进制数转换成八进制。
方法1
#include<stdio.h>
int main(){
int i,n,m[1000];
scanf("%d",&n);
for(i=0;i<n;i++){
scanf("%x",&m[i]);//输入为16进制数
}
for(i=0;i<n;i++){
printf("%o\n",m[i]);//输出为8进制数
}
return 0;
}
方法2
#include<stdio.h>
int fact(int n){ //利用16进制转10进制再将10进制转8进制解决
if(n<8) //此行代码将10进制转为8进制
return n;
else
return fact(n/8)*10+n%8;
}
long fun(char *s){ //以下代码将16进制转为10进制
int i,t;
long sum=0;
for(i=0;s[i];i++){
if(s[i]>='0'&&s[i]<='9')
t=s[i]-'0';
if(s[i]>='a'&&s[i]<='z')
t=s[i]-'a'+10;
if(s[i]>='A'&&s[i]<='Z')
t=s[i]-'A'+10;
sum=sum*16+t;
}
return fact(sum);
}
int main(){
int m[50],n,i;
char s[50];
scanf("%d",&n);
for(i=0;i<n;i++){
scanf("%s",s);
m[i]=fun(s);
}
for(i=0;i<n;i++){
printf("%d\n",m[i]);
}
return 0;
}
2082: [蓝桥杯][基础练习]十六进制转十进制
题目描述
从键盘输入一个不超过8位的正的十六进制数字符串,将它转换为正的十进制数后输出。
注:十六进制数中的10~15分别用大写的英文字母A、B、C、D、E、F表示。
输入
一个十六进制数
输出
对应得十进制
样例输入
FFFF
样例输出
65535
#include <stdio.h>
int main(){
int n;
scanf("%x",&n);//输入为16进制数
printf("%d",n);
return 0;
}
2083: [蓝桥杯][基础练习]十进制转十六进制
题目描述
十六进制数是在程序设计时经常要使用到的一种整数的表示方式。它有0,1,2,3,4,5,6,7,8,9,A,B,C,D,E,F共16个符号,分别表示十进制数的0至15。十六进制的计数方法是满16进1,所以十进制数16在十六进制中是10,而十进制的17在十六进制中是11,以此类推,十进制的30在十六进制中是1E。
给出一个非负整数,将它表示成十六进制的形式。
输入
输入包含一个非负整数a,表示要转换的数。0<=a<=2147483647
输出
输出这个整数的16进制表示
样例输入
- 30
样例输出
- 1E
方法1
#include <stdio.h>
int main(){
int n;
scanf("%d",&n);
printf("%x",n);
return 0;
}
方法2
#include<stdio.h>
int main() {
int n, temp, i, t, j;
char a[100];
while(scanf("%d", &n) != EOF) {
if(n == 0)
printf("%d", n);
temp = n;
i = 0;
while(temp > 0) {
t = temp%16;
if(t < 10) {
a[i] = t+'0';
}else{
a[i] = t-10+'A';
}
temp /= 16;
i++;
}
for(j = i-1; j >= 0; j--)
printf("%c", a[j]);
printf("\n");
}
return 0;
}
2084: [蓝桥杯][基础练习]特殊回文数
题目描述
123321是一个非常特殊的数,它从左边读和从右边读是一样的。
输入一个正整数n, 编程求所有这样的五位和六位十进制数,满足各位数字之和等于n 。
输入
输入一行,包含一个正整数n。
数据规模和约定
1<=n<=54。
输出
按从小到大的顺序输出满足条件的整数,每个整数占一行。
样例输入
52
样例输出
899998
989989
998899
#include <stdio.h>
int main(){
int n,i,a[10]={0};
scanf("%d",&n);
int b,c,j;
for(i=10000;i<=999999;i++){//所有的5位或6位数
b=i;//多用一个变量,只用一个变量的话,值在里循环会变掉
c=0;//循环一次就要将累加器清零
for(j=0;j<6;j++){//最高为6位,提取各位数字并相加
a[j]=b%10;
b=b/10;//实现将已取出的位数删掉
c=c+a[j];
}
if((i<99999)&&(a[0]==a[4]&&a[1]==a[3]&&c==n)){
printf("%d\n",i);//输出的是符合条件的5位数
}
if((i>=100000)&&(a[0]==a[5]&&a[1]==a[4]&&a[2]==a[3]&&c==n)){
printf("%d\n",i);//输出的是符合条件的6位数
}
}
return 0;
}
2085: [蓝桥杯][算法提高VIP]P1003
题目描述
作为一名网络警察,你的任务是监视电子邮件,看其中是否有一些敏感的关键词。不过,有些狡猾的犯罪嫌疑人会改变某些单词的字母顺序,以逃避检查。请编写一个程序,发现这种调整过顺序的关键词。程序的输入有两行,第一行是关键词列表,第二行是待检查的句子。程序的输出为在该句子中所找到的经过顺序调整的关键词。(单词全部为小写,单词之间以一个空格分隔,每一行的单词个数不限)
输入
两行,第一行表示关键词,空格隔开
第二行是待检查的内容
输出
输出找到的经过顺序的关键词
样例输入
- guns mines missiles
- aameric ssell snug dan iimsssle ot sit neeemis
样例输出
- guns missiles
#include<stdio.h>
int main(){
int key[1000][26]; ///用来存放每个关键词的某个单词的个数
int sen[26]; ///存放检索的句子中某个单词的个数
char str1[1000]; ///存放第一个字符串
char str2[1000]; ///存放第二个字符串
char temp[1000][100]; ///存放关键词
int a[1000];
int i,j,k;
while(gets(str1)){
gets(str2);
memset(a,0,sizeof(a));
memset(key,0,sizeof(key));
j=0;
for(i = 0; i < strlen(str1); i++){ ///关键词
k = 0;
while(str1[i]!=' '&&str1[i]!='\0'){
temp[j][k]=str1[i];
key[j][str1[i]-'a']++;
i++;
k++;
}
temp[j][k]='\0';
j++;
}
for(i = 0; i < strlen(str2); i++){
memset(sen,0,sizeof(sen));
while(str2[i]!=' '&&str2[i]!='\0'){
sen[str2[i]-'a']++;
i++;
}
for(k = 0; k < j; k++){
if(a[k]==0){
int flag = 1,t1;
for(t1=0;t1<26;t1++){
if(key[k][t1]!=sen[t1]){
flag = 0;
break;
}
}
if(flag)
a[k]=1;
}
}
}
for(i = 0;i < j; i++){
if(a[i]){
printf("%s",temp[i]);
break;
}
}
i++;
for(;i < j; i++){
if(a[i]){
printf(" %s",temp[i]);
}
}
printf("\n");
}
return 0;
}
2086: [蓝桥杯][算法提高VIP]最长公共子序列
题目描述
给定两个字符串,寻找这两个字串之间的最长公共子序列。
输入
输入两行,分别包含一个字符串,仅含有小写字母。
输出
最长公共子序列的长度。
样例输入
abcdgh
aedfhb
样例输出
3
思路
- 递归:当数组a和b对应位置字符相同时,则直接求解下一个位置;
否则,取两种情况中的较大数值。
#include<stdio.h>
char a[100],b[100];//定义字符串数组
int m,n;
int cmp(int i,int j){
if(i>=m|| j>=n) return 0;//出口
if(a[i] == b[j]) return 1+cmp(i+1,j+1);//直接求解下一个位置
else //取两种情况中的较大数值
return cmp(i+1,j) > cmp(i,j+1) ? cmp(i+1,j) : cmp(i,j+1);
}
int main(){
scanf("%s%s",&a,&b);//输入字符串
m=strlen(a);//获取字符串长度
n=strlen(b);
printf("%d",cmp(0,0));//输出子串长度
return 0;
}
2087: [蓝桥杯][算法提高VIP]8皇后·改
题目描述
规则同8皇后问题,但是棋盘上每格都有一个数字,要求八皇后所在格子数字之和最大。
输入
一个8*8的棋盘。
输出
所能得到的最大数字和
样例输入
1 2 3 4 5 6 7 8
9 10 11 12 13 14 15 16
17 18 19 20 21 22 23 24
25 26 27 28 29 30 31 32
33 34 35 36 37 38 39 40
41 42 43 44 45 46 47 48
48 50 51 52 53 54 55 56
57 58 59 60 61 62 63 64
样例输出
260
**参考**柳神的代码
#include <stdio.h>
int max = 0;
int pic[8][8],i,j;
int cmp(int pos[], int row) {
for(i = 0; i < row; i++) {
if(pos[i] == pos[row] || abs(i - row) == abs(pos[i] - pos[row]))
return 0;
}
return 1;
}
void dfs(int pos[], int row) {
if(row == 8) {
int sum = 0;
for(i = 0; i < 8; i++) {
sum += pic[i][pos[i]];
}
max = sum > max ? sum : max;
return ;
}
for(pos[row] = 0; pos[row] < 8; pos[row]++) {
if(cmp(pos, row)) {
dfs(pos, row + 1);
}
}
}
int main() {
int pos[8];
for(i = 0; i < 8; i++) {
for(j = 0; j < 8; j++) {
scanf("%d",&pic[i][j]);
}
}
dfs(pos, 0);
printf("%d\n",max);
return 0;
}
2088: [蓝桥杯][算法提高VIP]快速幂
题目描述
给定A, B, P,求(A^B) mod P。
输入
输入共一行。
第一行有三个数,N, M, P。
输出
- 输出共一行,表示所求。
- 共10组数据
- 对100%的数据,A, B为long long范围内的非负整数,P为int内的非负整数。
样例输入
2 5 3
样例输出
2
#include <stdio.h>
int main() {
long long n,m;
int p,i,sum=1;
scanf("%lld %lld %d",&n,&m,&p);
while(m){
if(m%2==1){
sum=(sum*n)%p;
}
m>>=1;//把m的二进制位向右移一位,再赋值,其实就是将m的值除以2,如6>>1就是把00000110右移一位变为00000011,结果是3
n=(n*n)%p;
}
printf("%d\n",sum);
return 0;
}
2091: [蓝桥杯][算法提高VIP]3-2求存款
题目描述
接受两个数,一个是用户一年期定期存款金额,一个是按照百分比格式表示的利率,计算一年期满后的本金与利息总额。说明:(1) 存款金额以人民币元为单位,精确到分;(2) 输入利率时不输入百分号,例如利率为3.87%,用户直接输入3.87;(3) 按照国家法律,存储利息所得需缴纳5%的所得税,计算结果时应当扣除所得税。(4) 显示的结果精确到人民币分。
注意:数据须用float表示;计算结果须保存到一个float变量中,再用printf输出。
输入
-
一行,以一个空格隔开的两个浮点数。
-
输入数据中每一个数的范围。本金<100000000,利息<100
输出
一个浮点数。
样例输入
5000.00 5.00
样例输出
5237.50
#include <stdio.h>
int main() {
float a,b,sum=0;
scanf("%f %f",&a,&b);
printf("%.2f",a+a*0.95*b/100.0);
return 0;
}
2089: [蓝桥杯][算法提高VIP]不大的数
题目描述
在当今的大数据时代,超大数的高精度计算已经成为众多领域的热门研究之一。现在T校也想在此领域有所造诣已造福于全社会,然而由于时间有限,所以短时间内难以找出大数计算的通用算法,于是学校找到了同学中的“神霸”——你来帮忙,并仅要求你能在数并不算大的时候给出结果。又出于某种特殊需要,也并不要求你给出数的全部结果,而只是要求结果的前10位(注意不是后10位),并考虑到2的幂次的特殊性和典型性,所以要你计算的数均为2的幂次。
输入
- 一个自然数n。
- 数据规模和约定
- 0<=n<=10000000
输出
- 2的n次幂的前10位。
样例输入
- 60
样例输出
- 1152921504
思路
- 已知求 res=2^n ,遇到大的幂次方,可以利用对数来转化问题,两边对10取对数可得 :
lg(res)=lg(2^n)=nlg(2)
, - 如果2^n的位数小于十位直接输出即可
- 否则取对数后,去掉整数部分,对小数进行pow即可,然后取前十位即可;
- pow() 函数用来求 x 的 y 次方的值
#include <stdio.h>
int main(){
double n;
scanf("%lf",&n);
double a=log2(1000000000);
if(n<a){
printf("%lld\n",(long long)pow(2.0,n));
return 0;
}
double res=n*log10(2)-(long long)(n*log10(2));
res=pow(10.0,res);
while(res<1000000000){
res=res*10;
}
printf("%lld\n",(long long)res);
return 0;
}
2090: [蓝桥杯][算法提高VIP]最长字符序列
题目描述
设x(i), y(i), z(i)表示单个字符,则X={x(1)x(2)……x(m)},Y={y(1)y(2)……y(n)},Z={z(1)z(2)……z(k)},我们称其为字符序列,其中m,n和k分别是字符序列X,Y,Z的长度,括号()中的数字被称作字符序列的下标。
如果存在一个严格递增而且长度大于0的下标序列{i1,i2……ik},使得对所有的j=1,2,……k,有x(ij)=z(j),那么我们称Z是X的字符子序列。而且,如果Z既是X的字符子序列又是Y的字符子序列,那么我们称Z为X和Y的公共字符序列。
在我们今天的问题中,我们希望计算两个给定字符序列X和Y的最大长度的公共字符序列,这里我们只要求输出这个最大长度公共子序列对应的长度值。
举例来说,字符序列X=abcd,Y=acde,那么它们的最大长度为3,相应的公共字符序列为acd。
输入
- 输入一行,用空格隔开的两个字符串
输出
- 输出这两个字符序列对应的最大长度公共字符序列的长度值
样例输入
- aAbB aabb
样例输出
- 2
思路:找到公共字符序列,统计它的长度,输出
#include <stdio.h>
#include <string.h>
int max(int a, int b){//自定义max函数
if(a>b) return a;
return b;
}
int main(){
char a[100],b[100];
int i,j;
scanf("%s %s",a,b);
int c[100][100]={0};
for(i=1;i<=strlen(a);i++){//求字符串的长度
for(j=1;j<=strlen(b);j++){
if(a[i-1]==b[j-1]){
c[i][j]=c[i-1][j-1]+1;
}else{
c[i][j]=max(c[i][j-1],c[i-1][j]);
}
}
}
printf("%d",c[strlen(a)][strlen(b)]);
return 0;
}