[NOIP1999]回文数——(C语言)

一、题目

题目描述

若一个数(首位不为零)从左向右读与从右向左读都一样,我们就将其称之为回文数。

例如:给定一个10进制数56,将56加65(即把56从右向左读),得到121是一个回文数。

又如:对于10进制数87:

STEP1:87+78  = 165                  STEP2:165+561 = 726

STEP3:726+627 = 1353                STEP4:1353+3531 = 4884

在这里的一步是指进行了一次N进制的加法,上例最少用了4步得到回文数4884。

写一个程序,给定一个N(2<=N<=10或N=16)进制数M(100位之内),求最少经过几步可以得到回文数。如果在30步以内(包含30步)不可能得到回文数,则输出“Impossible!”

进制N>10时,使用大写'A'字母表示10,'B'表示11,...,'E'表示15

输入描述:
两行,分别为N,M
输出描述:
STEP=ans

示例1

输入
9
87
输出
STEP=6

二、C语言完整代码

#include
#include
#include
void add(char *s,char *s2,int n);
void opposide(char *s,char *s2);
int judge(char *s);
int main()
{
    int n;
    char s[110],s2[110];
    scanf("%d",&n);//输入 n 进制的数 s
    getchar();
    scanf("%s",s);
    int step=0;
    if(judge(s)) {printf("STEP=%d",step);return 0;}
    while(1)
    {
        step++;
        opposide(s,s2);
        add(s,s2,n);
        if(judge(s)){printf("STEP=%d",step);return 0;}
        if(step==30){printf("Impossible!"); return 0;}
    }
}
void opposide(char *s,char *s2)
{
    int n=strlen(s);
    int i;
    for(i=0;i=0;i--)
    {
        if(c[i]!=0) break;
    }
    n=i+1;
    i=0;
    while(1)
    {
        if(c[i]==0&&i>=n) break;
        if(c[i]>=x) 
        {
            c[i+1]+=c[i]/x;c[i]%=x;
        }
        i++;
    }
    n=i;
    for(i=0;i=0&&c[n-i-1]<=9) s[i]=c[n-i-1]+'0';
        else s[i]=c[n-i-1]+'A'-10;
    }
    s[n]='\0';
}

三、解析

1.程序可能输入不同进制的数,可能出现当进制大于10时可能出现字母,所以输入的数要作为字符串类型进行输入

    scanf("%d",&n);//输入 n 进制的数 s
    getchar();
    scanf("%s",s);

2.自定义函数judge 判断s字符串是否是回文数

int judge(char *s) //判断是否回文数,返回值 是1 否0
{
    int n=strlen(s);
    int i;
    for(i=0;i

注意是字符串s而不是整数int类型的 

3.自定义opposide函数 将字符串s1倒序放入字符串s2

void opposide(char *s,char *s2)
{
    int n=strlen(s);
    int i;
    for(i=0;i

4.自定义add函数,将正序字符串s和倒序字符串s2以n进制的数相加

void add(char *s,char *s2,int x)
{
    int n=strlen(s);
    int c[110]={0};
    int i;
    for(i=0;i=0;i--)
    {
        if(c[i]!=0) break;
    }
    n=i+1;
    i=0;
    while(1)
    {
        if(c[i]==0&&i>=n) break;
        if(c[i]>=x) 
        {
            c[i+1]+=c[i]/x;c[i]%=x;
        }
        i++;
    }
    n=i;
    for(i=0;i=0&&c[n-i-1]<=9) s[i]=c[n-i-1]+'0';
        else s[i]=c[n-i-1]+'A'-10;
    }
    s[n]='\0';
}

这一段自定义函数比长,分开来看

4.1

将s和s2 字符串以数的类型相加存入c数组,c数组为int类型,所以可以存储大于等于10的数,我们在后面再次对c数组进行处理。

我们此时存入c数组按照倒序存入,方便后面的进位计算。

for(i=0;i

4.2

处理进位,按照进制进位。该位保留余数,整除数给下一位加上。

i=0;
while(1)
    {
        if(c[i]==0&&i>=n) break;
        if(c[i]>=x) 
        {
            c[i+1]+=c[i]/x;c[i]%=x;
        }
        i++;
    }

4.3

最后把c数组存入s字符串就可以了

n=i;
    for(i=0;i=0&&c[n-i-1]<=9) s[i]=c[n-i-1]+'0';
        else s[i]=c[n-i-1]+'A'-10;
    }
    s[n]='\0';

s是字符串数组,而c是整数型数组,进行转换即可。

你可能感兴趣的:(c语言,算法,开发语言)