3

Hey everyone I've got a char array which holds an ID field. The id field looks as follows i0001. I want to increment the ID by one when i create a new link in my linked list.

So I sort through the linked list to the last value, which is for example; i0005, now I want to create my new field as i0006. Obviously I can't just increment the value of the array because it's a char, how should I go about this?

char id[5];

I tried:

id[4] = id[4]+1;

The issue with this is it doesn't increment id[3] when it hits 10, instead it starts replacing the numerical value with symbols (i assume these are the ascii values after number).

Anyone got any idea of how they would approach this? I'm a bit stumped!

Ryan
  • 33
  • 1
  • 6
  • 3
    If the format is constant, i.e. `iXXX` then you can simply get rid of `i` (move pointer to the string by one), convert string to number (use `strtol()` function), increase the number by 1 and finally write it back to string (use `sprtinf()` function). – Crozin Oct 13 '15 at 12:02
  • 6
    I would store it as a number and generate an id string as needed. – molbdnilo Oct 13 '15 at 12:07
  • 1
    I agree with @molbdnilo. However, if you are going to do this - `id[4] = id[4]+1;` - don't: instead, use `++id[4];`. A sane compiler would optimise them to be the same, but why type more when you don't have to? – underscore_d Oct 13 '15 at 12:11
  • @molbdnilo: with the (possibly important) side note that these are not valid strings to begin with. – Jongware Oct 13 '15 at 12:12
  • It's not a good idea to increase on string values. As when you have a value `0009`, would you turn this to `0010`. Using an `int` value maybe a better solution. And it's not hard to turn the int to a string you want. – luoluo Oct 13 '15 at 12:14
  • Definitely, the problem you cited is why this thread exists! My suggestion was more general, that we'd want to avoid referencing any variable multiple times when simpler operators exist (increment, etc.). It makes typing/reading easier (& might slow a _really_ bad _theoretical compiler) – underscore_d Oct 13 '15 at 12:23

4 Answers4

2

Implementing carry by yourself should be good.

void inclementArray(char *id) {
    int i;
    for (i = 4; i >= 1; i--) {
        id[i]++;
        if (id[i] > '9') {
            id[i] = '0';
            /* do carry and proceed to next digit */
        } else {
            /* no carry, the calculation is completed */
            break;
        }
    }
}

Note: char id[5]; is sufficient for storing {'i', '0', '0', '0', '5'}, but it is insufficient to store null-terminated string "i0005".

MikeCAT
  • 73,922
  • 11
  • 45
  • 70
0

Here is a simple program which will give you an idea how to do that -

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

int main(void){
   char id[6]="i0001";            // your id 
   char a[5];                     // array to hold first part of id
   int i;                         // integer variable to hold number (non-zero)
   sscanf(id,"%[^1-9]%d",a,&i);   // assign non zero number to i
   i=i+1;                         // add 1 to i 
   sprintf(id,"%s%d",a,i);        // store both a and i again into id
   printf("%s",id);
}

Check output here.

ameyCU
  • 16,489
  • 2
  • 26
  • 41
0

Something like this:

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

#define PREFIX "i"

int main(void)
{
    char id[] = "i0001";
    printf("before: %s\n", id);
    int digit = atoi(strtok(id, PREFIX));
    ++digit;
    snprintf(id, sizeof(id), "%s%04d", PREFIX, digit);
    printf("after: %s\n", id);
    exit(0);
}
Arkadiusz Drabczyk
  • 11,227
  • 2
  • 25
  • 38
0

Doing simply like this

id[4] = id[4]+1;

will not carry to the next digit. You must carry it yourself, but that of course need many more lines of code.

A simple way is to convert the number to value, increase and print back

char id[] = "i0005";
int idval;

sscanf(id, "i%d", &idval);
snprintf(id, sizeof(id), "i%d", idval+1);

Alternatively scan the number ignoring the i prefix like this

scanf(id+1, "%d", &idval);
snprintf(id+1, sizeof(id)-1, "%d", idval+1);
phuclv
  • 37,963
  • 15
  • 156
  • 475