0

Assuming I have a structure such as:

typedef struct {
    int a;
    int b;
} TEST1_T;

TEST1_T test1;

I can reference test1.a with ((int**)&test1)[0]

And if i have a structure such as:

typedef struct {
    int a[15];
    int b[20];
    int c[30];
} TEST2_T;

TEST2_T test2;

How can i reference test2.c with it's order in struct like reference test1.b with ((int**)&test1)[1]?

FreeFO
  • 1
  • 1
  • Use the `offsetof` macro from `` to get the offset in bytes from the beginning of the struct to one of the members. – user3386109 Aug 12 '22 at 03:14
  • `offsetof` requires you to have the name of the member. This question is asking about accessing a member by a numerical index. – Michael M. Aug 12 '22 at 03:18
  • 2
    What are you really trying to do? This sounds like an [XY Problem](https://meta.stackexchange.com/questions/66377/what-is-the-xy-problem) – selbie Aug 12 '22 at 03:39
  • Why do you want to do this? If a or b arrays increase in size, this sort of reference will just keel over. – cup Aug 12 '22 at 05:14
  • 1
    Strictly speaking, `((int**)&test1)[0]` results in *undefined behavior* because the effective type of `test1` is `TEST1_T` and it is being accessed using an lvalue expression of incompatible type `int`. See C11/C17 6.5/6-7. – Ian Abbott Aug 12 '22 at 08:20
  • 1
    @IanAbbott: `((int**)&test1)[0]` does not attempt to access the memory using an expression of type `int`; it attempts to access the memory using an expression of type `int *`. If the cast were to `int *`, the behavior would be defined, because C 2018 6.7.2.1 15 says that a pointer to a structure “suitably converted” yields a pointer to its first member, which is an `int`, so the aliasing rule would be satisfied. – Eric Postpischil Aug 12 '22 at 10:32
  • 1
    @EricPostpischil Good point. I think OP and myself meant `((int*)&test1)[0]`. Your reference makes this access OK, but using `((int*)&test1)[1]` to access the `b` member would be undefined. – Ian Abbott Aug 12 '22 at 10:37

1 Answers1

0

I would consider using a union, in this case. You could even use C11's new anonymous union.

#include <stdio.h>

union test1 {
    struct { int a, b; };
    int x[2];
};

union test2 {
    struct { int a[15], b[20], c[30]; };
    int x[15 + 20 + 30];
};

int main(void) {
    union test1 foo = { { 4, 5 } };
    printf("%d %d / %d %d\n", foo.a, foo.b, foo.x[0], foo.x[1]);
    return 0;
}
Neil
  • 1,767
  • 2
  • 16
  • 22