0

What I want to do is: The user inputs a string with commas; for example: 123456,44,55,,66

and I want to separate it and store in a new array without the commas; for example:

m[0][]={123456}, m[1][]={44}, m[2][]={55}, m[3][]={}, m[4][]={66}

123456 is the student ID number, 44 is the mark for 1st module, 55 is the mark for 2nd module, NULL means that the student didn't take that 3rd module, and 66 is the mark for 4th module.

How can I exactly do that? What I know is that by detecting double commas, it means the student didn't take that 3rd module.

Here is what I have written so far:

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

void copystring(char m[],char temp[]);

main()
{
    char temp[10000];
    char m[10000][10000];
    gets(temp);
    copystring(m,temp);
    printf("%s\n",m);           
    return 0;
}

void copystring(char m[],char temp[])
{
    int i;
    int j;
    for (j=0;j<(strlen(temp));j++)
    {
        for (i=0;i<(strlen(temp));i++)
        {
            if (temp[i]!=*(",")&&temp[i]!=*(" "))
            {
                m[j][i]=temp[i];
            }   
        }
    }
}
Melika Barzegaran
  • 429
  • 2
  • 9
  • 25
Michael Tan
  • 81
  • 13
  • Your call to `copystring(char **, char *)` is not defined. – smac89 Dec 19 '13 at 08:28
  • Where are you stuck? what are you missing - please you be specific? – NiRR Dec 19 '13 at 08:29
  • 2
    Don't use [gets()](http://stackoverflow.com/questions/1694036/why-is-the-gets-function-dangerous-why-should-it-not-be-used). – moeCake Dec 19 '13 at 08:30
  • Smac89,sorry but I don't really know how to define it correctly. NiRR,sorry but I am not sure whether there is a problem in my codes and I don't know how to correct it. Could you please help me to check on it? – Michael Tan Dec 19 '13 at 08:33
  • moeCake,what should I use? – Michael Tan Dec 19 '13 at 08:34
  • Adding to @moeCake : Didn't you get warning: `gets() is dangerous, Use fgets() instead` – 0xF1 Dec 19 '13 at 08:38
  • That's probably the first time I see someone write `*(",")` in C. You need to read more basic tutorial material on the language. A single character constant should be written as `','` (single quotes, not double). – unwind Dec 19 '13 at 08:59
  • @unwind : Also, to mention more clearly, Use `temp[i]!= ','` instead of `temp[i]!=*(",")`. He might take it as `temp[i]!=*(',')`. – 0xF1 Dec 19 '13 at 09:03
  • It's not clear why you're using arrays to store a single element like m[1][]={44}, why not m[1]=44 ? – Ramy Al Zuhouri Dec 19 '13 at 11:16

5 Answers5

1

I have edited my code so that you can understand how to declare a function prototype containing 2D array as parameter. Also use fgets() instead of gets(). The function returns the number of marks read , i.e. an integer. I think this might help. Run the code and look on the man pages or google to understand fgets() better.

#include <stdio.h>
#include <string.h>
#include <ctype.h>
#define SIZE 1000
int stringcopy(char m[][SIZE],char temp[]);
main()
{
        char temp[SIZE],m[100][SIZE];
        fgets(temp,SIZE,stdin);
        int num=stringcopy(m,temp);
        int i;
        for(i=0;i<num;++i)
                printf("%s\n",m[i]);
        return 0;
}
int stringcopy(char m[][SIZE],char temp[]) {
        int len=strlen(temp);
        int i,j=0,k=0;
        for(i=0;i<len;++i) {
                if(temp[i]!=',')
                        m[j][k++]=temp[i];
                else {
                        m[j][k]='\0';
                        ++j;
                        k=0;
                }
        }
        m[j][k-1]='\0';
        return j+1;
}
alDiablo
  • 969
  • 7
  • 22
  • It didn't works. =( I want to make it like m[0][]={123456},m[1][]={44},m[2][]={55},m[3][]={},m[4][]={66}. – Michael Tan Dec 19 '13 at 09:06
  • I ran the above code and got thefollowin output : 123456 44 55 66 It means that m[0] ={123456} , m[1]={44} , m[2] = {55} and m[3]= {} and m[4] = {66} . Doesn't it suffice your problem ?? – alDiablo Dec 19 '13 at 09:09
  • I got this warning:arithmetic on pointer to an incomplete type m[j][k++]=temp[i] – Michael Tan Dec 19 '13 at 09:25
  • Actually in your main function , you are passing m (a 2d array) to copystring (which takes 1d array) , as you defined the prototype wrong. Just copy and paste my whole program and run it. Then you will understand the problem in your code. – alDiablo Dec 19 '13 at 09:54
  • Can you please teach how should I defined the prototype correctly. I run your program, the last for loop only print out m[0], if print it one by one, it works. printf("%s\n",m[0]); printf("%s\n",m[1]); and so on... – Michael Tan Dec 19 '13 at 10:10
  • @user3118123- I have edited my code to include function prototypes. Hope it helps. – alDiablo Dec 19 '13 at 10:48
  • thanks a lot! just want to ask why must it be m[100][SIZE], I try m[SIZE][SIZE] but the program cannot runs. How is this possible? – Michael Tan Dec 19 '13 at 11:23
  • @user3118123- its not at all compulsory.SIZE only bounds the number of marks you can hold and you can keep it whatever you want. Infact m[SIZE][SIZE] runs just fine on my machine. Can u tell what error do you get ? – alDiablo Dec 19 '13 at 11:38
  • I can't tell from my compiler. When I run my program, the message "xxx.c has just stopped working" popped out. I use C-Free 4.0 – Michael Tan Dec 19 '13 at 11:46
  • Oh. Try reducing the size. It will work. It may be because of the array of dimensions 1000*1000 . – alDiablo Dec 19 '13 at 11:49
1

You have to solve your problem in different steps,

The first step is to check how many tokens you have in your input string to be able to allocate enough space to store an array of tokens.

Then you should extract the tokens of the input strings in your tokens string array. To extract the tokens from your input string, you can use the strtok function from <string.h>.

Finally you can use your tokens however you want, like converting them to long in your case.

EDIT: given the requirements, here is a small implementation of what you could do. I don't check the returns of the malloc, you maybe should do it.

int main(int argc, char** argv) {
    int i;

    char* input_string = /* your input string for somewhere */;

    char** tokens;
    int tokens_count = 0;
    char* input_ptr = input_string;

    char* tmp_token;
    size_t tmp_token_length;

    // count the occurences of your separtor to have the number of elements
    for(; input_ptr[tokens_count]; input_ptr[tokens_count] == ',' ? tokens_count++ : input_ptr++);

    if(tokens_count == 0) {
        // no tokens found, what do you want to do here ?
    }
    else {
        // build our tokens array
        tokens = malloc(sizeof(*tokens) * tokens_count);
        i = 0;

        tmp_token = strtok(input_string, ',');
        while(tmp_token != NULL) {
            tmp_token_length = strlen(tmp_token);

            if(tmp_token_length != 0) {
                tokens[i] = malloc(tmp_token_length);
                strcpy(tokens[i], tmp_token);
            }
            else {
                tokens[i] = NULL;
            }

            i++;
            tmp_token = strtok(input_string, ',');
        }

        // populate your array of arrays of integers
        long** m = malloc(sizeof(long*) * tokens_count);

        for(i=0; i<tokens_count; i++) {
            char* tmp_token = tokens[i];

            if(tmp_token == NULL) {
                m[i] = NULL;
            }
            else {
                m[i] = malloc(sizeof(long));
                m[i][0] = strtol(tmp_token, NULL, 10);
            }
        }
    }
}

However, you should probably change your data structure by using structures instead of a massive array.

nesderl
  • 325
  • 1
  • 5
  • Well I think you want to say "converting", "casting" string to integer is not possible. ;-) – 0xF1 Dec 19 '13 at 09:00
  • Yes these functions convert string to integer, casting is the term use to denote data type change done by using *cast* operator. – 0xF1 Dec 19 '13 at 09:22
  • that's being picky, but true it is indeed converting. – nesderl Dec 19 '13 at 09:25
0
for (j=0;j<(strlen(temp));j++)
{
    for (i=0;i<(strlen(temp));i++)
    {
        if (temp[i]!=(',')&&temp[i]!=(' '))
        {
            m[j][i]=temp[i];
        }   
        else{
            m[j][i]='\0';break;// must end a string with null character.
        }
    }
}

and for priting use

printf("%s",m[0]);// make a loop for it
AJ.
  • 4,526
  • 5
  • 29
  • 41
0

Try to use scanf for getting input, your copystring function seems fine; but if there is a problem then debug it to see what the problem is.

Naz Ekin
  • 347
  • 6
  • 17
  • Put a breakpoint at the beginning of the function then run in debug mode. Which compiler do you use? – Naz Ekin Dec 19 '13 at 09:20
-1

You can read entire string using fgets, or scanf and then use strtok(string, ",") to get substrings between commas.

To detect if student has missed some entry, there are many ways, few of them are:

1) Check no. of sub-strings you get before strtok returns NULL.
2) You can search for substring ,, using strstr in the input string.

0xF1
  • 6,046
  • 2
  • 27
  • 50
  • To the user who downvoted: I have added more to my answer, please review it. – 0xF1 Dec 19 '13 at 08:35
  • can you please show me the entire codes? thanks. I don't really understand how to use strtok and strstr – Michael Tan Dec 19 '13 at 08:50
  • It is not that difficult, just refer to [strtok](http://www.cplusplus.com/reference/cstring/strtok/), here you can find help for `strstr` also. Giving you entire codes will not help unless you know their purpose. – 0xF1 Dec 19 '13 at 08:54