4

Is it possible to declare a variable implicitly in an initialization? Perhaps like so:

struct S
{
  void *a;
  void *b;
};

struct S test = {&(int), &(float) };

void testfunc (void)
{ 
  *(test.a) = -2;
  *(test.b) = 1.3;
}

Advantages (in my eyes):

  1. No additional lines needed for explicit declaration
  2. Implicit variables are protected in the struct, no external access.
3
  • 6
    No it's not possible to do anything like that. Unless you dynamically allocate memory of course. Also, you can't dereference void* without casting. Commented Aug 31, 2016 at 8:44
  • 6
    No, this is not possible. Commented Aug 31, 2016 at 8:46
  • 1
    More importantly, it is not meaningful. Yes you could set the void pointers to point at compound literals, but the struct contains no type information so that achieves nothing. What is the actual problem you are trying to solve? Your two so-called "advantages" are nonsense and not true. You might want to look at opaque types. Commented Aug 31, 2016 at 13:10

2 Answers 2

5

Yes it is possible, since C99. Your guess was very close; but it is required to provide a braced initializer even if you plan to assign another value later:

struct S test = { &(int){0}, &(float){0} };

This feature is called compound literal. A compound literal is an lvalue.

Note that your testfunc contains an error though; since a has type void *, you cannot write *(test.a). You could either change S to have int *a; float *b;, or you'll have to cast at the point of writing, e.g. *(int *)test.a = 5;.

Sign up to request clarification or add additional context in comments.

6 Comments

With compound literals values cannot be modified. It seems that OP wants to change the value dereferenced during execution.
@LP: The standard gives an example (not normative, but indicative): The following three expressions have different meanings: "/tmp/fileXXXXXX"(char []){"/tmp/fileXXXXXX"}(const char []){"/tmp/fileXXXXXX"}The first always has static storage duration and has type array of char, but need not be modifiable; the last two have automatic storage duration when they occur within the body of a function, and the first of these two is modifiable. There is also discussion of const-qualified compound literals. This clearly indicates that compound literals can be modified.
I have a followup question, and maybe I should post this separately, but it's pretty closely related. I often use const configuration structures that contain a pointer to modifiable status structures. Can this same method be applied there with named initialization in the status? i.e. struct status { int count; }; struct config { struct status *stat; }; struct config cfg = { &(struct status){.count = 256} };
@rjp You didn't include const anywhere in your example, but yes you can do that.
@M.M Ooops, I must have deleted it accidentally. It was supposed to be const struct config cfg. Comments probably weren't the right venue for a question with that much code in it. Thanks for the clarification, though.
|
1

No, that is not possible. The address-of operator requires an actual existing symbol as its argument.

The C11 draft says:

The operand of the unary & operator shall be either a function designator, the result of a [] or unary * operator, or an lvalue that designates an object that is not a bit-field and is not declared with the register storage-class specifier.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.