简体   繁体   中英

C Flatten 2-D Array of Char* to 1-D

Say I have the following code:

char* array[1000]; // An array containing 1000 char*

// So, array[2] could be 'cat', array[400] could be 'space', etc.

Now, how could I flatten this array into 1-D? Is it possible to do this such that new_1D_array[2] would still be 'cat', new_1D_array[400] would still be 'space', etc.?

You have a one-dimensional array of type pointer-to-char , with 1000 such elements. It's already 1D as far as arrays go, though it could be interpreted as a "jagged 2D array". If you want to convert this into one massive character array, you could do something like so, which requires calculating the size of the buffer you'll need to store it, and then flattening the array.

Note that if you opt to use malloc instead of calloc , you'll have to manually set the last character to '\\0' or 0 so that the final result is a NULL-delimited C-style string, and not just a character array, as the latter of the two won't work with C string operations, and the former will.

Code Listing


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

int main(void) {
        const char* array[] = { "one", "two", "three", "four" };
        size_t length = sizeof(array) / sizeof(char*);

        int i;
        int sum = 0;
        int count = 0;

        for (i=0; i<length; i++) {
                printf("Element #%d - %s\n", i, array[i]);
                sum += strlen(array[i]) + 1;
        }
        sum++;  // Make room for terminating null character

        char* buf;
        if ((buf = calloc(sum, sizeof(char))) != NULL) {
                for (i=0; i<length; i++) {
                        memcpy(buf+count, array[i], strlen(array[i]));
                        count += strlen(array[i]) + 1;
                        buf[count-1] = '#';
                }
                printf("Output Buffer: %s\n", buf);
                printf("Buffer size:%d - String Length:%d\n", sum, strlen(buf));
                free(buf);
                buf = NULL;
        }

        return 0;
}

Sample Output


Element #0 - one
Element #1 - two
Element #2 - three
Element #3 - four
Output Buffer: one#two#three#four#
Buffer size:20 - String Length:19

The above answer beat me to the puch and looks great, but I'll finish my thoughts here.

In this version every 11th byte of flatArray will contain the start of the strings from the original array, making it very easy to find the original strings from the ones before - ie string index 2 would start at 2*11 == index 22 and string 400 would start at 400 * 11 == index 4400 . In this way, you would not need to iterate through the flat array counting terminators to find your old strings. The cost of this being that the flat array takes a bit more memory than the original.

char* array[1000];

// Malloc new buffer
char *flatArray = malloc(length * 1100);

for(i=0; i<1000; i++)
{  
    strncpy(&flatArray[i * 11], array[i], 10);
    flatArray[i * 11 + 10] = '\0';
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM