training

Code I wrote during training
git clone git://git.bitsmanent.org/training
Log | Files | Refs | README

mystrconv.c (5278B)


      1 /* Exercise 8.27 */
      2 
      3 #include <stdio.h>
      4 #include <string.h>
      5 #include <ctype.h>
      6 
      7 double atof(const char *nptr);
      8 int atoi(const char *nptr);
      9 long atol(const char *nptr);
     10 double strtod(const char *nptr, char **endptr);
     11 long strtol(const char *nptr, char **endptr, int base);
     12 unsigned long strtoul(const char *nptr, char **endptr, int base);
     13 
     14 int main(void)
     15 {
     16    char n[] = "11537463.948abc", *strp;
     17    double num;
     18    long lnum;
     19 
     20    int b = 10;
     21 
     22    printf("atof(\"%s\") = %f\n", n, atof(n));
     23    printf("atoi(\"%s\") = %d\n", n, atoi(n));
     24    printf("atol(\"%s\") = %ld\n", n, atol(n));
     25 
     26    num = strtod(n, &strp);
     27    printf("strtod(\"%s\", &strp) = %f (strp: %s)\n", n, num, strp);
     28 
     29    lnum = strtol(n, &strp, b);
     30    printf("strtol(\"%s\", &strp, %d) = %ld (strp: %s)\n", n, b, lnum, strp);
     31 
     32    lnum = strtoul(n, &strp, b);
     33    printf("strtoul(\"%s\", &strp, %d) = %lu (strp: %s)\n", n, b, lnum, strp);
     34 
     35    return 0;
     36 } /* E0F main */
     37 
     38 /* Convert ASCII string to double */
     39 double atof(const char *nptr)
     40 {
     41    double ret;
     42    int i, n = atoi(nptr), p_val = 1;
     43    double d = 1;
     44    char *c;
     45 
     46    /* Calculate the positional value */
     47    for(p_val = 1; p_val < n; p_val *= 10)
     48       ; /* Empty body */
     49 
     50    p_val /= 10; /* Toggle the latest (exceded) value */
     51 
     52    /* Calculate the decimal numbers */
     53    for(ret = 0, i = 0; i < (int)strlen(nptr); i++) {
     54       if( !isdigit((int)nptr[i]) ) {
     55 	 ++i; /* Go to.. */
     56 	 c = (char *) &nptr[i]; /* ..the next position */
     57 	 break;
     58       }
     59 
     60       ret += (int)(nptr[i] - '0') * p_val;
     61       p_val /= 10;
     62    }
     63 
     64    n = atoi(c); /* To be continue.. :-) */
     65 
     66    /* Calculate the floating point numbers */
     67    for(i = 0; i < (int)strlen(c); i++) {
     68       if( !isdigit((int)c[i]) ) {
     69 	 break;
     70       }
     71 
     72       d *= 0.1;
     73    }
     74 
     75    ret += n * d; /* Add the floating point numbers */
     76 
     77    return ret;
     78 } /* eof atof() */
     79 
     80 /* Converti ASCII string to integer */
     81 int atoi(const char *nptr)
     82 {
     83    int i, n = 0;
     84    long m = 1;
     85 
     86    /* count the numbers for the m size */
     87    for(i = 0; i < (int)strlen(nptr); i++) {
     88       if( !isdigit( (int)nptr[i] ) )
     89 	 break;
     90       m *= 10;
     91    }
     92    m /= 10;
     93 
     94    /* Creating the integer */
     95    for(i = 0; i < (int)strlen(nptr); i++) {
     96       if( !isdigit( (int)nptr[i] ) )
     97 	 break;
     98 
     99       n += (nptr[i] - '0') * m;
    100       m /= 10;
    101    }
    102 
    103    if(nptr[0] == '-')
    104       return -n;
    105    return n;
    106 } /* eof atoi() */
    107 
    108 /* Convert ASCII string to long */
    109 long atol(const char *nptr)
    110 {
    111    long ret;
    112    int i, n = atoi(nptr), p_val = 1;
    113 
    114    /* Calculate the positional value */
    115    for(p_val = 1; p_val < n; p_val *= 10)
    116       ; /* Empty body */
    117 
    118    p_val /= 10; /* Toggle the latest (exceded) value */
    119 
    120    /* Calculate the decimal numbers */
    121    for(ret = 0, i = 0; i < (int)strlen(nptr); i++) {
    122       if( !isdigit((int)nptr[i]) ) {
    123 	 break;
    124       }
    125 
    126       ret += (int)(nptr[i] - '0') * p_val;
    127       p_val /= 10;
    128    }
    129 
    130    return ret;
    131 } /* eof atol() */
    132 
    133 /* Convert ASCII string to double */
    134 double strtod(const char *nptr, char **endptr)
    135 {
    136    double ret, d = 1;
    137    int i, n = atoi(nptr), p_val = 1;
    138    char *c;
    139 
    140    /* Calculate the positional value */
    141    for(p_val = 1; p_val < n; p_val *= 10)
    142       ; /* Empty body */
    143 
    144    p_val /= 10; /* Toggle the latest (exceded) value */
    145 
    146    /* Calculate the decimal numbers */
    147    for(ret = 0, i = 0; i < (int)strlen(nptr); i++) {
    148       if( !isdigit((int)nptr[i]) ) {
    149 	 ++i; /* Go to.. */
    150 	 c = (char *) &nptr[i]; /* ..the next position */
    151 	 break;
    152       }
    153 
    154       ret += (int)(nptr[i] - '0') * p_val;
    155       p_val /= 10;
    156    }
    157 
    158    n = atoi(c); /* To be continue.. :-) */
    159 
    160    /* Calculate the floating point numbers */
    161    for(i = 0; i < (int)strlen(c); i++) {
    162       if( !isdigit((int)c[i]) ) {
    163 	 break;
    164       }
    165 
    166       d *= 0.1;
    167    }
    168    endptr[0] = (char *) &c[i];
    169 
    170    ret += n * d; /* Add the floating point numbers */
    171 
    172    return ret;
    173 }
    174 
    175 
    176 /* Convert ASCII string to long */
    177 long strtol(const char *nptr, char **endptr, int base)
    178 {
    179    long ret;
    180    int i, n = atoi(nptr), p_val = 1;
    181 
    182    /* Skip all numbers <= 5 */
    183    if(base <= 5) {
    184       endptr[0] = (char *) nptr;
    185       return 0;
    186    }
    187 
    188    /* Calculate the positional value */
    189    for(p_val = 1; p_val < n; p_val *= base)
    190       ; /* Empty body */
    191 
    192    if(base <= 7) p_val /= base; /* A little fix */
    193 
    194    /* Calculate the decimal numbers */
    195    for(ret = 0, i = 0; i < (int)strlen(nptr); i++) {
    196       if( !isdigit((int)nptr[i]) ) {
    197 	 break;
    198       }
    199 
    200       ret += (nptr[i] - '0') * p_val;
    201       p_val /= base;
    202    }
    203    ret /= base; /* Toggle a zero */
    204 
    205    endptr[0] = (char *) &nptr[i];
    206 
    207    return ret;
    208 } /* eof strtol() */
    209 
    210 /* Convert ASCII string to unsigned long */
    211 unsigned long strtoul(const char *nptr, char **endptr, int base)
    212 {
    213    unsigned long ret;
    214    int i, p_val = 1, n = atoi(nptr);
    215 
    216    /* Skip all numbers <= 5 */
    217    if(base <= 5) {
    218       endptr[0] = (char *) nptr;
    219       return 0;
    220    }
    221 
    222    /* Calculate the positional value */
    223    for(p_val = 1; p_val < n; p_val *= base)
    224       ; /* Empty body */
    225 
    226    if(base <= 7) p_val /= base; /* A little fix */
    227 
    228    /* Calculate the decimal numbers */
    229    for(ret = 0, i = 0; i < (int)strlen(nptr); i++) {
    230       if( !isdigit((int)nptr[i]) ) {
    231 	 break;
    232       }
    233 
    234       ret += (nptr[i] - '0') * p_val;
    235       p_val /= base;
    236    }
    237    ret /= base; /* Toggle a zero */
    238 
    239    endptr[0] = (char *) &nptr[i];
    240 
    241    return ret;
    242 } /* eof strtol() */
    243