Hacker Newsnew | past | comments | ask | show | jobs | submitlogin

You can do it even faster with the if statements:

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

    int main(int argc, char *argv[])
    {
        if (argc < 2) {
            fprintf(stderr, "Usage: %s <string>\n", argv[0]);
            return 1;
        }

        char *s = argv[1];
        int i;

        /* find the end of the string */
        for (i = 0; s[i] != '\0'; ++i)
            ;

        /* make sure the string wasn't empty */
        if (i == 0) {
            fprintf(stderr, "Error: empty string\n");
            return 1;
        }

        /* last character is at s[i - 1] */
        char d = s[i - 1];

        if (d == '0')
            printf("even\n");
        if (d == '1')
            printf("odd\n");
        if (d == '2')
            printf("even\n");
        if (d == '3')
            printf("odd\n");
        if (d == '4')
            printf("even\n");
        if (d == '5')
            printf("odd\n");
        if (d == '6')
            printf("even\n");
        if (d == '7')
            printf("odd\n");
        if (d == '8')
            printf("even\n");
        if (d == '9')
            printf("odd\n");
    
        return 0;
    }

gcc -std=c11 -Wall -Wextra -O2 -o check_digit check_digit.c

./check_digit 999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999





You can do it even even faster by replacing your if statements (works because the ascii values end in the digit they represent):

    if (d & 1)
       printf("odd\n");
    else 
       printf("even\n")

You inspired me this joyful rewrite:

    #define _(e) { e;};
    #define r(e) _(return e)
    #define I(b, e) _(if (b) r(e));
    #define W(e) _(while (1) _(e));
    int main(int c, char **v) {
      _(I(c != 2, -1) _(c = 0) W(I(!v[1][c++], v[1][c - 2] & 1)))
    }

probably easier in bash:

    number="$1"
    if [[ "$number" =~ "^(2|4|6|8|10|12|14|16|18|20)$" ]]; then
        echo even
    elif [[ "$number" =~ "^(1|3|5|7|9|11|13|15|17|19)$" ]]; then
        echo odd
    else
        echo Nan
    fi
A bit limited, but you can scale it up

Scaled up:

  case "$1" in
    *0|*2|*4|*6|*8) echo even;;
    *) echo odd;;
  esac
If $1 had a trailing non-digit, or was empty, that would indeed be an odd situation!

I'm disappointed, it's not in rust. :-)

Still hoping for the C++ template version. Don’t pay for what you don’t use!



Guidelines | FAQ | Lists | API | Security | Legal | Apply to YC | Contact

Search: