0

I'm trying to create a generic linked list in C that has multiple data fields

typedef struct listNode {
void *data1;
void *data2;
void *data3;
struct listNode *next;
} listNode;

I need to read from a file in the format

name YOB  country 
john 1995 USA
Sam  1990 USA
Tim 1889 AUS

So my plan was to make each node of the list store the info on each line (I've already taken care of finding what kind of variable each column is so I can just type cast the pointer). So for example on line 2

typedef struct listNode {
void *data1;   //becomes a string that is john
void *data2;   //becomes a int that is 1995
void *data3;   // becomes a string that is USA
struct listNode *next;
} listNode;

My issue is firstly is that even possible or can each element of the list only hold one kind of variable as when I search generic lists, examples only have one void data*

My second issue is that I don't know how many columns the file will have; is there a way to dynamically set the number of data fields?

//FILE HAS 5 COLUMNS
typedef struct listNode {
void *data1;
void *data2;
void *data3;
void *data4;
void *data5;
struct listNode *next;
} listNode;

//FILE HAS 2 COLUMNS
typedef struct listNode {
void *data1;
void *data2;
struct listNode *next;
} listNode;
marc_s
  • 732,580
  • 175
  • 1,330
  • 1,459
CrispyCashew
  • 99
  • 2
  • 9
  • Is the number of colm going to be constant throughout the file? – Saurav Sahu Oct 19 '16 at 03:30
  • @Saurav Sahu Yes it will be – CrispyCashew Oct 19 '16 at 03:32
  • Answer is NO for dynamic struct formation as its data types must be known at compile time : Checkout http://stackoverflow.com/questions/6187908/is-it-possible-to-dynamically-define-a-struct-in-c – Saurav Sahu Oct 19 '16 at 03:34
  • @ Saurav Sahu oh ok, if I knew how many columns there are ( lets say 3 like in the first example) the list can contain different types of variables right? – CrispyCashew Oct 19 '16 at 03:43
  • 1
    Normally, you'd use a single `void *data;` in the list, but the list for your triplet would point to a structure with the three fields. Hence: `struct listNode { void *data; struct listNode *next; };` and `struct person { char name[20]; int yob; char country[20]; };` or thereabouts, and the `void *` values managed would be `struct person *` in disguise. The same list code can handle single elements, double, triple, quadruple, quintuple, … – Jonathan Leffler Oct 19 '16 at 04:10
  • right ok thats a good way of doing it. But what If I dont know the variable type of each column but only how many there were. Thats why my original list node had 3 void* data types so they could be typre casted – CrispyCashew Oct 19 '16 at 04:39

2 Answers2

1

I didn't quite get your first issue. Maybe some more explanations?

And for the second one, you will need to dynamically allocate something to store all columns and in the list structure, a pointer to the allocated memory. Below is an example:

typedef struct listNode_s {
    void **columns;
    size_t columnsCount;
    struct listNode_s *next;
} listNode;

And when creating a list node:

void **columns = malloc(sizeof(void*) * count);
for(i=0; i < count; ++i) {
    columns[i] = get_column(i);
}
listNode *node = malloc(sizeof(listNode));
node->columns = columns;
node->columnsCount = count;
//Insert the node to your list

//When freeing your node
free(node->columns);
free(node);

P.S. Maybe using a union + enum for type instead of a void* for data is better.

王致远
  • 61
  • 3
  • sorry, so it seems like a basic question but if my list was typedef struct listNode { void *data1; //becomes a string that is john void *data2; //becomes a int that is 1995 void *data3; // becomes a string that is USA struct listNode *next; } listNode; can data1 be a int data2 be a string data3 be a char Or do they all have to be the same type of varible – CrispyCashew Oct 19 '16 at 04:27
  • @CrispyCashew of course they can be of different types. The member of a struct can be any type, like in my example, listNode has two members and the first is a pointer to void* and the second is a size_t (an unsigned int type mostly used for counting things). – 王致远 Oct 19 '16 at 05:38
-1

If you want to create one generic list, you could refer to the list definition of Linux kernel.

include/linux/list.h

linuxer
  • 326
  • 4
  • 14