how would i detect if an element is an array? also, how would i declare an array like this: [1, 2, 3, [4, 5, 6]]
?
You don't.
In C, multidimensional arrays are arrays of arrays, not an array where one element is another array but the others are numbers. int x[10][10]
declares x
as an array of 10 arrays of 10 int
s, i.e. 100 total elements in a 10 x 10 matrix.
To do what you describe, you'd need an array of void *
s:
struct myarr {
size_t len;
void **arr;
};
You allocate len
elements for arr
with x.arr = malloc(x.len * sizeof(void *))
. Then each element can be anything you want - perhaps a number, perhaps another struct myarr
for further nesting.
In practice, however, you'll have no way of knowing whether the void *
is a number or another array. So you'll need some sort of dynamic type checking.
enum mytype {
INT,
ARR,
};
Then you make a struct myint
and redo struct myarr
to be compatible:
struct myint {
enum mytype type;
int i;
};
struct myarr {
enum mytype type;
size_t len;
enum mytype **arr;
};
When you make a struct myint
, always set x.type = INT
, and when you make a struct myarr
, always set x.type = ARR
.
struct
pointers can always be cast to a pointer to the first element, so both struct myint *
and struct myarr *
can be cast to an enum mytype *
pointer, which is what your array in myarr
holds. Then, when you access an element of the array with .arr[n]
, you can test (at runtime) what type it holds, cast the pointer accordingly, and use at will:
for(size_t i = 0; i < x.len, i++)
{
enum mytype *j = x.arr[i];
if(*j == INT)
{
printf("%i", ((struct myint *)j)->i);
}
else if(*j == ARR)
{
printf("[");
// recurse
printf("]");
}
else /* this should not happen, you messed up */;
}
There are various other ways to achieve fundamentally the same thing.