Array of strings

This is a discussion on Array of strings within the C Programming forums, part of the General Programming Boards category; I saw a couple of postings about his and that got me thinking and I got a little confused. How ...

  1. #1
    the Corvetter
    Join Date
    Sep 2001
    Posts
    1,584

    Array of strings

    I saw a couple of postings about his and that got me thinking and I got a little confused. How do you create an array of strings? Would it be:
    Code:
    char *string[5];  /* This??? */
    char **string;  /* This??? */
    char string[][5];  /* This ??? */
    Thanks...

    --Garfield
    1978 Silver Anniversary Corvette

  2. #2
    Registered User steve_i83's Avatar
    Join Date
    Aug 2001
    Posts
    42
    what you need is an array of char pointers... because thats what a string is , its a pointer to a block of data containing the data. thus i think you need

    char *mystring[5];

    this is an array of 5 char *

    also note: mystring is also a char * now...
    C Rulz!

  3. #3
    and the hat of wrongness Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    32,548
    More world renowned Salem© examples....

    Code:
    #include <stdio.h>
    
    int main ( ) {
        // you have 5 pointers, but you can point to strings of any length
        char *string1[5] = {
            "a", "string", "array",
            "of", "variable-length-strings"
        };
    
        // this is a pointer to anything which looks like *string1[n]
        // you could also use string2 as the starting point for
        // creating dynamically allocated strings using malloc
        char **string2 = string1;
    
        // you can have as many strings as you like []
        // but each one must be <= 4 chars to allow the \0 to fit in [5] chars
        char string3[][5] = {
            "this","aray","can","only",
            "hold","smal","word","type",
            "str-","ings"
        };
        int i;
    
        for ( i = 0 ; i < 5 ; i++ ) {
            printf( "s1[%d]=%s\n", i, string1[i] );
            printf( "s2[%d]=%s\n", i, string2[i] );
        }
        for ( i = 0 ; i < 10 ; i++ ) {
            printf( "s3[%d]=%s\n", i, string3[i] );
        }
        return 0;
    }
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.
    I support http://www.ukip.org/ as the first necessary step to a free Europe.

  4. #4
    the Corvetter
    Join Date
    Sep 2001
    Posts
    1,584
    So, it is just like any array with the brackets to signify more than one?
    Code:
    int newInt[5];  /* An array of 5 integers */
    char *newString[5];  /* An array of 5 strings */
    Okay, that's easy enough.

    One more question (going off the subject a little bit). It you have this:
    Code:
    int *intPtr;  /* Then I have to allocate memory for it with malloc */
    intPtr = malloc(sizeof(int));
    intPtr = 4;  /* initialize intPtr */
    
    /* But if I have a char pointer (or as we know, as string) */
    char *string;  /* How come I don't have to allocate memory for
    --this char pointer? */
    So, my question is, why do you have to dynamically allocate memory for, let's say, an int pointer and NOT a char pointer? Thanks...

    --Garfield
    1978 Silver Anniversary Corvette

  5. #5
    Guest Sebastiani's Avatar
    Join Date
    Aug 2001
    Location
    Waterloo, Texas
    Posts
    5,708
    Well you DON'T have to allocate for an int pointer! That is simply the choice YOU the programmer choose to do if you want to be nice to system resourses, because you can "free" the memory you allocate for, but not for memory you don't. While allocating( and later de-allocating) is definately a good habit to get into, it is hardly necessary unless 1) You are working with a large program that will need many variables and thus threatens to crash the system at runtime , or 2) You are working with a system that runs many programs at once, etc, 3) etc.

    If you are developing a program that will need say 100 int variables declared and used, for instance, should you decide to not allocate for them, you will effectively be tying up around one tenth of a kilobyte! Pocket-change system resourses really!

    Of course now if you are needing 100 structs, the story can be quite different. Depending on their sizes, this could mean one tenth of a megabyte(or perhaps much higher!).

    Also remember that if you declare a non- malloced variable from within a function, once the routine passes out of this function, the system has probably "de-allocated" the variable anyway!

    So the choice is yours.

    I would recommend mallocing most strings, most or all structs and buffers(looooong strings), etc.

    By the way, as far as I know, you DO have to malloc a string pointer if you intend to de-allocate it later.

    Oh and the syntax for the all important aspect of de-allocation(for why malloc if you are not going to de-allocate it???) is
    " free(this_int); " ...assuming you malloced an int called "this_int".
    Code:
    #include <cmath>
    #include <complex>
    bool euler_flip(bool value)
    {
        return std::pow
        (
            std::complex<float>(std::exp(1.0)), 
            std::complex<float>(0, 1) 
            * std::complex<float>(std::atan(1.0)
            *(1 << (value + 2)))
        ).real() < 0;
    }

  6. #6
    and the hat of wrongness Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    32,548
    > So, my question is, why do you have to dynamically allocate memory for, let's say, an int pointer and NOT a char pointer?
    But you do have to allocate.

    You're mistaking allocation for initialisation. All my previous examples were initialisation. Any pointer (of any type) has to be either initialised or allocated before you can use it.

    Using ints
    Code:
    int fred;
    int *ptr;
    
    ptr = &fred;   // initialise
    ptr = malloc( sizeof(int) );  // allocate
    
    // with either init or allocate done, this is now valid
    *ptr = 42;  // use
    Using strings.
    Code:
    char message[20];
    char *ptr;
    
    ptr = message;  // initialise
    ptr = malloc( 20*sizeof(char) );  // allocate
    
    // with either init or allocate done, this is now valid
    strcpy( ptr, "hello world" );
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.
    I support http://www.ukip.org/ as the first necessary step to a free Europe.

  7. #7
    Registered User larry's Avatar
    Join Date
    Sep 2001
    Posts
    96
    Could I ask for one thing here?

    Why do I have to allocate '20 * sizeof(char)' bytes in Salem's example? I mean, char is one byte large, isn't it? (ASCII - 255 chars.) So (20 * sizeof(char)) == 20 and then I think I can write malloc(20), is that ok?
    Please excuse my poor english...

  8. #8
    and the hat of wrongness Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    32,548
    > So (20 * sizeof(char)) == 20 and then I think I can write malloc(20), is that ok?
    It is, but if you always write "n*sizeof(type)", then you're less likely to miss the "*sizeof(type)" when it really matters.

    int *ptr = malloc( 20 );
    will cause you just as much grief (perhaps even more) than if you hadn't allocated anything at all.
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.
    I support http://www.ukip.org/ as the first necessary step to a free Europe.

  9. #9
    Registered User larry's Avatar
    Join Date
    Sep 2001
    Posts
    96
    > int *ptr = malloc( 20 );
    > will cause you just as much grief (perhaps even more) than if you hadn't allocated anything at all.

    Sure. That's not what I meant. I meant "char *ptr = malloc(20)" which allocates 20 bytes so I can store 19 characters plus terminator in it (as far as I took from you explanation).
    Please excuse my poor english...

  10. #10
    Registered User
    Join Date
    Sep 2001
    Posts
    32
    btw, is it good practice to put

    char *str;

    str = ( char *) malloc(n *sizeof(char));

    instead of
    str = malloc(n *sizeof(char)); ???

    i saw the first in a book and use it like that eversince. is it reduntant now? (the book was a bit old-fashioned)

    thanx

    null

  11. #11
    Registered User larry's Avatar
    Join Date
    Sep 2001
    Posts
    96
    I know I have to put (char*) type-cast there, I only forgot it now. That's not my point. I just wanted to ensure char is 1 byte long...

    thanx anyway
    Please excuse my poor english...

  12. #12
    Unregistered
    Guest
    Garfield, this code:

    int *intPtr; /* Then I have to allocate memory for it with malloc */
    intPtr = malloc(sizeof(int));
    intPtr = 4; /* initialize intPtr */

    will not run. the last line is the problem.

    there is no buil-in type for arrays in c. this is why we use the pointer stuff.

    the intPtr is the name of the array. it is also a pointer to the first ellement of the array. ie intPtr holds the -address- of the array (in fact the address of the first ellement of the array but because they are stored sequencialy that's all you need).

    so intPtr contains a hex number, which is the memory address of the array. you cannot assign an absolute number to a pointer (intPtr =4).

    when you say int *intPtr, you just decalre a pointer. it doesnt contain any value yet. now, that pointer to int you can make it point to a single integer or an array of them.

    for 1 integer you can say

    intPtr = malloc( 1*sizeof(int));

    or
    int k;
    intPtr = &k;

    in the first you use malloc to allocate space for the int that intPtr will point. in the second case you dont need malloc since k already exists.

    again in the first case, if you want to assing a value to the int you allocated, you say

    *intPtr = 100; (or whatever value).

    in the second case, intPtr points to k. so you can use:

    k=100;

    or
    *intPtr =100;


    similarly for arrays
    intPtr = malloc( 100*sizeof(int));

    creates an array of 100 ints. intPtr is the address of the first element of the array. intPtr+1 is the address of the second element of the array and so on.

    *intPtr, gives you the value of the first element, *(intPtr+1) the value of the second and so on.

    you can use *(intPtr+index) to read or set an element in the array.

    hope that helps

    null

  13. #13
    Registered User
    Join Date
    Sep 2001
    Posts
    32
    larry, i was just asking people of this thread or whoever if it's still used or not so i stop use it if it's not necessary.

    wasnt meaning that you have to use it or that you forgot it or anything like that...

    could be my english (not first language)

    regards

    null

  14. #14
    zen
    zen is offline
    of Zen Hall zen's Avatar
    Join Date
    Aug 2001
    Posts
    1,007
    btw, is it good practice to put

    char *str;

    str = ( char *) malloc(n *sizeof(char));

    instead of
    str = malloc(n *sizeof(char)); ???
    You don't need the typecast in C.
    zen

  15. #15
    the Corvetter
    Join Date
    Sep 2001
    Posts
    1,584
    So, I understand, Salem. I either have to initialize or allocate the pointer. But, wouldn't initializing an int ptr to 4 being initializing?:
    Code:
    int *ptr_to_int;
    *ptr_to_int = 4; /* Wouldn't this be initializing? */
    I believe that this code flagged an error that ptr_to_int was not initialized or something. But I can do this?:
    Code:
    int num = 4;
    int *ptr_to_int;
    ptr_to_int = &num;  /* This is legal??? */
    But if I wanted to do the first set of code, would I have to do this?:
    Code:
    int *ptr_to_int;
    ptr_to_int = malloc (sizeof(int));
    ptr_to_int = 4;  /* This is legal??? */
    Thanks.

    --Garfield
    1978 Silver Anniversary Corvette

Page 1 of 2 12 LastLast
Popular pages Recent additions subscribe to a feed

Similar Threads

  1. intializing an array of strings
    By doubty in forum C Programming
    Replies: 4
    Last Post: 06-19-2009, 12:59 PM
  2. Replies: 1
    Last Post: 03-19-2009, 10:56 AM
  3. Build an array of strings dynamically
    By Nazgulled in forum C Programming
    Replies: 29
    Last Post: 04-07-2007, 09:35 PM
  4. Array of strings in C
    By szill in forum C Programming
    Replies: 10
    Last Post: 02-22-2005, 04:03 PM
  5. Hi, could someone help me with arrays?
    By goodn in forum C Programming
    Replies: 20
    Last Post: 10-18-2001, 09:48 AM

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21