silkyit
silkyit

Reputation: 1

Palindrome number checking in c

Here is my code, I have many things to improve in my code, but my concern right now is to stop the program from crashing. Thanks in advance!

#include <stdio.h>

int IsPalindrome(int a);
int dec[20];
int a = 0;
int main()
{

    printf("Please insert your number:\n");
    scanf("%d", a);
    IsPalindrome(a);
  return 0;

}

int IsPalindrome(int a)
{
    int temp = 0;
    int count = 1;
    int p = 1;
    temp = a;
        while(temp > 10)
        {
            dec[count] = temp % 10;
            count = count+1;
            temp = temp / 10;
            printf("%d", count);
        }
    for(int i = 1; i < count; i++)
    {
            if (dec[i] != dec[count-i])
            {
                printf("Your number is not a Palindrome");
                return 1;
            }
    }
}

Side questions:

Upvotes: 0

Views: 243

Answers (2)

MikeCAT
MikeCAT

Reputation: 75062

  • int a = 0; scanf("%d", a); will lead to crush because it means it should store the data to somewhere which is invalid.
  • Use string to support large number.
  • If you won't use what your function returns, make the return type of function void. Note that the return type of main() should be int according to the standard.

Try this:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>

#define BUFFER_SIZE 512

char* ReadNumber(void);
void IsPalindrome(const char* a);
int main(void)
{
    char* a;
    printf("Please insert your number:\n");
    a = ReadNumber();
    IsPalindrome(a);
    free(a);
    return 0;

}

char* ReadNumber(void) {
    char* ret = malloc(BUFFER_SIZE);
    size_t allocatedSize = BUFFER_SIZE;
    size_t readLen = 0;
    if (ret == NULL)
    {
        perror("malloc");
        exit(1);
    }
    for (;;)
    {
        int c = getchar();
        if (!isdigit(c))
        {
            if (c != EOF) ungetc(c, stdin);
            break;
        }
        ret[readLen++] = c;
        if (readLen >= allocatedSize)
        {
            ret = realloc(ret, allocatedSize += BUFFER_SIZE);
            if (ret == NULL)
            {
                perror("realloc");
                exit(1);
            }
        }
    }
    ret[readLen] = '\0';
    return ret;
}

void IsPalindrome(const char* a)
{
    size_t count = strlen(a);
    /* can't write as i < count - i - 1 because size_t may be unsigned */
    for(size_t i = 0; i + i + 1 < count; i++)
    {
            if (a[i] != a[count - i - 1])
            {
                printf("Your number is not a Palindrome");
                return;
            }
    }
}

Upvotes: 1

lost_in_the_source
lost_in_the_source

Reputation: 11237

Another solution, would be to read the number as a string. Then reverse the string and see if the reversed string is lexicographically equal to the original string.

void strrev(char *s)
{
    char *start, *end;

    start = s;
    end = s + strlen(s) - 1;

    for (; end > start; --end, ++start) {
        char tmp;
        tmp = *start;
        *start = *end;
        *end = tmp;
    }
}
/* checks if string is a number. Only positive integers, or 0 */
int isnum(const char *s)
{
    int i;

    for (i = 0; s[i]; ++i)
        if (!isdigit(s[i]))
            return 0;

    return 1;
}
int main()
{
    char num[16], rev[16];
    fgets(num, 16, stdin);

    if (!isnum(num)) {
        fprintf(stderr, "not number\n");
        return 1;
    }

    strcpy(rev, num);
    strrev(rev);

    if (strcmp(rev, num) == 0)
        fprintf(stderr, "Palindrome\n");
    else fprintf(stderr, "No\n");
}

Upvotes: 0

Related Questions