1

I'm trying to get size of inner structure i.e. struct B. But I'm getting compilation error:

prog.c: In function ‘main’: prog.c:10:53: error: expected ‘)’ before ‘:’ token printf("%d | %d", sizeof(struct A), sizeof(struct A::struct B));

Following is my code:

#include <stdio.h>

struct A
{
        struct B{};
};

int main() {
    printf("%d | %d", sizeof(struct A), sizeof(struct A::struct B));
    return 0;
}

Could you suggest that how I can achieve this in C?

UPDATED

Answer from @Jabberwocky solves my above problem. But What about following code. This can also be found here:

#include <stdio.h>

struct A
{
    struct B{};
};

struct B
{};

int main() {
    printf("%d | %d", sizeof(struct A), sizeof(struct B), sizeof(struct A::struct B));
    return 0;
}

In this case I'm getting compilation error as following:

prog.c:8:8: error: redefinition of ‘struct B’
struct B
^
prog.c:5:10: note: originally defined here
struct B{};
^
prog.c: In function ‘main’:
prog.c:12:71: error: expected ‘)’ before ‘:’ token
printf("%d | %d", sizeof(struct A), sizeof(struct B), sizeof(struct A::struct B));

Here how I can diffrentiate between struct B and struct A::struct B

cse
  • 4,066
  • 2
  • 20
  • 37
  • For the second part of your question, read pmg's answer below. Short answer: you can't. – Jabberwocky Nov 16 '18 at 11:21
  • 2
    There is no `struct A::struct B`. C does not recognize `::` as a valid token; maybe you're thinking of C++? – pmg Nov 16 '18 at 11:31
  • @pmg I understand that because that is where I'm getting compilation error. This just to show that _What I wants to do?_. And Thanks!!! for your comment and answer :) – cse Nov 16 '18 at 11:32
  • C cannot fry eggs either ... well ... if you use a busy loop on a poorly insulated computer :-) – pmg Nov 16 '18 at 11:34
  • 1
    Please do not edit questions to ask new questions. When you have a new question, enter a separate new question. Stack Overflow is not a personal service for you; it is intended to create a durable repository of questions and answers. When future readers find your multiple-question question, it may be difficult for them to figure out which answers were written for your first question and which were written for your second question. – Eric Postpischil Nov 16 '18 at 12:12
  • @EricPostpischil I edited the question because it was in same context. I do't wanted to create confusion when I create a new question and it would be treated as _similar question_. – cse Nov 22 '18 at 05:59
  • @cse: Please do not edit questions to ask new questions. When you have a new question, enter a separate new question. – Eric Postpischil Nov 22 '18 at 12:27

2 Answers2

6
#include <stdio.h>

struct A
{
        struct B{};   // this should not compile anyway in C as C
                      // does not allow empty structs
                      // but this would compile: struct B{int a;};
};

int main() {
    printf("%d | %d", sizeof(struct A), sizeof(struct B));
                                           // just write struct B
    return 0;
}

Working sample:

#include <stdio.h>

struct A
{
  int b;
  struct B { int a; };
};

int main() {
  printf("%d | %d", sizeof(struct A), sizeof(struct B));
  return 0;
}

Possible output on a 32 bit system:

8 | 4
Jabberwocky
  • 48,281
  • 17
  • 65
  • 115
  • `this should not compile anyway in C` C does support nested structs as far as I know? – DeiDei Nov 16 '18 at 11:10
  • @DeiDei yes it does, but C does not allow _empty_ structs and `struct B{}` is clearly empty. – Jabberwocky Nov 16 '18 at 11:11
  • 2
    @cse a standard compliant C compiler would not compile this: Look [here](https://www.godbolt.org/z/uLBQx-). But in C++ it compiles. It's a gnu C extension. Read this: https://stackoverflow.com/a/24685483/898348 – Jabberwocky Nov 16 '18 at 11:17
  • @Jabberwocky The provided link is having invalid code as line `printf("%d | %d", sizeof(struct A), sizeof(struct A::struct B));`. This is the line where I'm getting compilation error in my question. To verify _if C compiler supports inner structure_, Change it to `printf("%d ", sizeof(struct A));` and it will compile. – cse Nov 16 '18 at 11:29
  • 1
    @cse empty structs are not allowed in standard C, but gnu c (gcc) supports them as an extension. – Jabberwocky Nov 16 '18 at 11:41
  • 2
    @cse -- "To verify _if C compiler supports inner structure_,.... ": you can't verify if a compiler supports something by running code in C. You need to appeal to documentation, since undefined behavior can include the appearance of working code. In this case, while _nested_ structures are supported in C, [empty structures are not, leading to undefined behavior](https://port70.net/~nsz/c/c11/n1570.html#6.7.2.1p8). – ad absurdum Nov 16 '18 at 11:42
  • @DavidBowling and Jabberwocky, Thanks for your comments. I'll keep it in mind. – cse Nov 16 '18 at 11:50
4

Be aware that C support for nested structures is logical only. Each structure exists on its own.

#include <stdio.h>
struct A {                   // same as
    int bar;                 // struct B { int foo };
    struct B { int foo; } b; // struct A { int bar; struct B b; };
};

int main(void) {
    struct A a;
    a.bar = 42;
    a.b.foo = -1;
    printf("a.bar is %d; a.b.foo is %d\n", a.bar, a.b.foo);

    struct B b; /* struct B is visible outside struct A */
    b.foo = 666;
    printf("b.foo - a.bar is %d\n", b.foo - a.bar);
    return 0;
}

https://ideone.com/rHaanj

pmg
  • 106,608
  • 13
  • 126
  • 198