Need to seperate input scanf()

Discussion in 'C Programming' started by ern, Sep 20, 2005.

  1. ern

    ern Guest

    I'm using scanf("%s",userInput) to capture up to three words from the
    user. I want to seperate those three words into three variables:

    char * firstWord;
    char * secondWord;
    char * thirdWord;

    Is there an easy way/function that can do this already? Thanks!
    ern, Sep 20, 2005
    #1
    1. Advertising

  2. ern wrote on 20/09/05 :
    > I'm using scanf("%s",userInput) to capture up to three words from the
    > user. I want to seperate those three words into three variables:
    >
    > char * firstWord;
    > char * secondWord;
    > char * thirdWord;


    These variables are just uninitialized pointers. If you insist in using
    scanf(), you probably want a static or dynamic array of char.

    > Is there an easy way/function that can do this already? Thanks!


    fgets() and a hand made parser using strchr(), strstr() etc.

    Of course, there is a strtok() function that can be used to separate
    tokens, but it has many caveats.

    I think that POSIX.1 defines strtok_r() and strsep() that are better.
    But they are not standard and probably not portable everywhere.

    http://www.hmug.org/man/3/strtok_r.php


    --
    Emmanuel
    The C-FAQ: http://www.eskimo.com/~scs/C-faq/faq.html
    The C-library: http://www.dinkumware.com/refxc.html

    "It's specified. But anyone who writes code like that should be
    transmogrified into earthworms and fed to ducks." -- Chris Dollin CLC
    Emmanuel Delahaye, Sep 20, 2005
    #2
    1. Advertising

  3. ern

    ern Guest

    Isn't fgets() for files? I want to read from STDIN.
    ern, Sep 20, 2005
    #3
  4. ern wrote on 20/09/05 :
    > Isn't fgets() for files? I want to read from STDIN.


    I guess you meant stdin. fgets() is for stream. Surprise, stdin *is* a
    stream.

    --
    Emmanuel
    The C-FAQ: http://www.eskimo.com/~scs/C-faq/faq.html
    The C-library: http://www.dinkumware.com/refxc.html

    "It's specified. But anyone who writes code like that should be
    transmogrified into earthworms and fed to ducks." -- Chris Dollin CLC
    Emmanuel Delahaye, Sep 20, 2005
    #4
  5. ern

    ern Guest

    thanks. fgets and strtoks work pretty good. one more thing... how can
    I return an array of strings? I'd imagine the syntax would be
    something like:

    char *[ ] myFunction();
    ern, Sep 20, 2005
    #5
  6. ern wrote on 20/09/05 :
    > thanks. fgets and strtoks work pretty good. one more thing... how can
    > I return an array of strings? I'd imagine the syntax would be
    > something like:
    >
    > char *[ ] myFunction();


    No. There is no way to return an array in C[1]. All you can do is to
    return the address of the first element of some array. (but you neeed a
    way to know the limit : size, sentinel...).

    Note that the returned address must be valid after the leaving from the
    function. Hence, addresses local to the callee (called ?) are
    forbidden.

    -----------------
    [1] However, you can return a copy of a structure holding an array, but
    it's ugly and and more seriously inefficient and even unsafe if the
    size is big....

    --
    Emmanuel
    The C-FAQ: http://www.eskimo.com/~scs/C-faq/faq.html
    The C-library: http://www.dinkumware.com/refxc.html

    ..sig under repair
    Emmanuel Delahaye, Sep 21, 2005
    #6
  7. I would like to know if this code snippet effectively allocates and
    deallocates mem for the 2-D arr


    char** retStrArr(void)
    {
    char** arr;
    int i=0;
    arr = (char**) malloc(NUM_OF_STRINGS*sizeof(char*));
    for(i=0;i<NUM_OF_STRINGS;i++)
    {
    arr=(char*) malloc(STR_LENGTH*sizeof(char));
    /* strcpy(arr,"abc"); */
    }
    return arr;
    }

    int main(void)
    {
    int i=0
    char** arr=retStrArr();
    for(i=0;i<NUM_OF_STRINGS;i++)
    {
    free(arr);
    }
    free(arr);
    }

    Regards,
    Mohan S N
    Frodo Baggins, Sep 21, 2005
    #7
  8. Frodo Baggins wrote on 21/09/05 :
    > I would like to know if this code snippet effectively allocates and
    > deallocates mem for the 2-D arr
    >
    > char** retStrArr(void)
    > {
    > char** arr;
    > int i=0;
    > arr = (char**) malloc(NUM_OF_STRINGS*sizeof(char*));
    > for(i=0;i<NUM_OF_STRINGS;i++)
    > {
    > arr=(char*) malloc(STR_LENGTH*sizeof(char));
    > /* strcpy(arr,"abc"); */
    > }
    > return arr;
    > }
    >
    > int main(void)
    > {
    > int i=0
    > char** arr=retStrArr();
    > for(i=0;i<NUM_OF_STRINGS;i++)
    > {
    > free(arr);
    > }
    > free(arr);
    > }


    My compiler just told me that there is something wrong with your code :

    main.c:8: warning: no previous prototype for 'retStrArr'
    main.c: In function `retStrArr':
    main.c:11: error: implicit declaration of function `malloc'
    main.c:11: warning: nested extern declaration of `malloc'
    <internal>:0: warning: redundant redeclaration of 'malloc'

    main.c:11: error: `NUM_OF_STRINGS' undeclared (first use in this
    function)
    main.c:11: error: (Each undeclared identifier is reported only once
    main.c:11: error: for each function it appears in.)
    main.c:14: error: `STR_LENGTH' undeclared (first use in this function)

    main.c: In function `main_':

    main.c:23: error: syntax error before "char"
    main.c:24: error: `NUM_OF_STRINGS' undeclared (first use in this
    function)
    main.c:26: error: implicit declaration of function `free'
    main.c:26: warning: nested extern declaration of `free'
    main.c:26: error: `arr' undeclared (first use in this function)
    main.c:28: warning: nested extern declaration of `free'
    main.c:26: warning: redundant redeclaration of 'free'
    main.c:26: warning: previous implicit declaration of 'free' was here

    Please provide a compiling code if you want an evaluation...

    --
    Emmanuel
    The C-FAQ: http://www.eskimo.com/~scs/C-faq/faq.html
    The C-library: http://www.dinkumware.com/refxc.html

    "It's specified. But anyone who writes code like that should be
    transmogrified into earthworms and fed to ducks." -- Chris Dollin CLC
    Emmanuel Delahaye, Sep 21, 2005
    #8
  9. (supersedes <>)

    Frodo Baggins wrote on 21/09/05 :
    > I would like to know if this code snippet effectively allocates and
    > deallocates mem for the 2-D arr
    >
    > char** retStrArr(void)
    > {
    > char** arr;
    > int i=0;
    > arr = (char**) malloc(NUM_OF_STRINGS*sizeof(char*));
    > for(i=0;i<NUM_OF_STRINGS;i++)
    > {
    > arr=(char*) malloc(STR_LENGTH*sizeof(char));
    > /* strcpy(arr,"abc"); */
    > }
    > return arr;
    > }
    >
    > int main(void)
    > {
    > int i=0
    > char** arr=retStrArr();
    > for(i=0;i<NUM_OF_STRINGS;i++)
    > {
    > free(arr);
    > }
    > free(arr);
    > }


    My compiler just told me that there is something wrong with your code :

    main.c:8: warning: no previous prototype for 'retStrArr'
    main.c: In function `retStrArr':
    main.c:11: error: implicit declaration of function `malloc'
    main.c:11: warning: nested extern declaration of `malloc'
    <internal>:0: warning: redundant redeclaration of 'malloc'

    main.c:11: error: `NUM_OF_STRINGS' undeclared (first use in this
    function)
    main.c:11: error: (Each undeclared identifier is reported only once
    main.c:11: error: for each function it appears in.)
    main.c:14: error: `STR_LENGTH' undeclared (first use in this function)

    main.c: In function `main_':

    main.c:23: error: syntax error before "char"
    main.c:24: error: `NUM_OF_STRINGS' undeclared (first use in this
    function)
    main.c:26: error: implicit declaration of function `free'
    main.c:26: warning: nested extern declaration of `free'
    main.c:26: error: `arr' undeclared (first use in this function)
    main.c:28: warning: nested extern declaration of `free'
    main.c:26: warning: redundant redeclaration of 'free'
    main.c:26: warning: previous implicit declaration of 'free' was here

    Please provide a compiling code if you want an evaluation...

    Once fixed, and secured, the code is fine :

    #include <stdlib.h>

    #define NUM_OF_STRINGS 4
    #define STR_LENGTH 32

    static char **retStrArr (void)
    {
    char **arr = malloc (NUM_OF_STRINGS * sizeof *arr);

    if (arr != NULL)
    {
    int i = 0;

    for (i = 0; i < NUM_OF_STRINGS; i++)
    {
    arr = malloc (STR_LENGTH * sizeof *arr);
    sprintf (arr, "abc%d", i);
    }
    }
    return arr;
    }

    int main (void)
    {
    char **arr = retStrArr ();

    if (arr != NULL)
    {
    int i = 0;
    for (i = 0; i < NUM_OF_STRINGS; i++)
    {
    printf ("%s\n", arr);
    free (arr);
    }
    free (arr);
    }
    return 0;
    }

    --
    Emmanuel
    The C-FAQ: http://www.eskimo.com/~scs/C-faq/faq.html
    The C-library: http://www.dinkumware.com/refxc.html

    "There are 10 types of people in the world today;
    those that understand binary, and those that dont."
    Emmanuel Delahaye, Sep 21, 2005
    #9
  10. On 21 Sep 2005 10:09:32 -0700, "Frodo Baggins" <>
    wrote:

    >I would like to know if this code snippet effectively allocates and
    >deallocates mem for the 2-D arr
    >
    >
    >char** retStrArr(void)
    >{
    > char** arr;
    > int i=0;
    > arr = (char**) malloc(NUM_OF_STRINGS*sizeof(char*));


    You did specify effective.

    Don't cast the return from malloc. The only thing it does is
    prevent the compiler from warning you about undefined behavior if you
    forget to include a prototype for malloc.

    Check the return from malloc. You need to know if it succeeded.

    > for(i=0;i<NUM_OF_STRINGS;i++)
    > {
    > arr=(char*) malloc(STR_LENGTH*sizeof(char));


    Doyouenjoyreadinglongsentenceswithnospaces?

    sizeof(char) will always be 1.

    > /* strcpy(arr,"abc"); */
    > }
    > return arr;
    >}
    >
    >int main(void)
    >{
    > int i=0
    > char** arr=retStrArr();


    You need to check the return from the function to determine if it
    succeeded.

    > for(i=0;i<NUM_OF_STRINGS;i++)
    > {
    > free(arr);
    > }
    > free(arr);
    >}



    <<Remove the del for email>>
    Barry Schwarz, Sep 22, 2005
    #10
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Intaek LIM

    input values with scanf

    Intaek LIM, Aug 1, 2003, in forum: C Programming
    Replies:
    4
    Views:
    469
    Zoran Cutura
    Aug 6, 2003
  2. moondaddy
    Replies:
    2
    Views:
    569
    Steven Cheng[MSFT]
    Oct 16, 2006
  3. Replies:
    4
    Views:
    657
    Walter Roberson
    Sep 9, 2005
  4. =?ISO-8859-1?Q?Martin_J=F8rgensen?=

    scanf (yes/no) - doesn't work + deprecation errors scanf, fopen etc.

    =?ISO-8859-1?Q?Martin_J=F8rgensen?=, Feb 16, 2006, in forum: C Programming
    Replies:
    185
    Views:
    3,346
    those who know me have no need of my name
    Apr 3, 2006
  5. =?ISO-8859-1?Q?Martin_J=F8rgensen?=

    difference between scanf("%i") and scanf("%d") ??? perhaps bug inVS2005?

    =?ISO-8859-1?Q?Martin_J=F8rgensen?=, Apr 26, 2006, in forum: C Programming
    Replies:
    18
    Views:
    660
    Richard Bos
    May 2, 2006
Loading...

Share This Page