Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

Microsoft C++ syntax for union assignment at compile time

47 views
Skip to first unread message

Rick C. Hodgin

unread,
Jul 9, 2016, 11:31:56 PM7/9/16
to
I have something like this and I need to assign a value to the second member
of the union:

struct SAbc
{
int discriminator;

union {
int value;
char* ptr;
};
};

When I use it in source code, it's an example like this:

SAbc abc[] =
{
{ 1, 1 }, // Initializes discriminator, value
{ 2, "test" }, // Should initialize discriminator, ptr
};

I remember from GCC a syntax which was something like this:

{ 2, {.ptr = "test"} },

But I can't figure out how to get it to work in Microsoft's C++ compiler,
and I don't know what to search for to find it via Google.

Best regards,
Rick C. Hodgin

Mr Flibble

unread,
Jul 10, 2016, 12:06:08 AM7/10/16
to
Use boost.variant and then when it becomes available use std::variant.

/Flibble

Öö Tiib

unread,
Jul 10, 2016, 7:40:27 AM7/10/16
to
I am making three assumptions (assuming "yes" to three questions below).
1) PODs and aggregates are used to ensure that minimal run-time calls
are made?
2) 'char*' initialized from pointer to string literal won't be ever
used as pointer to mutable char?
3) discriminator is always 1 on case of int and always 2 on case of
string literal?

If I'm wrong, use 'boost::variant' instead of 'union' ... otherwise here
is my attempt:

// the class
struct SAbc
{
int discriminator;

union
{
int value;
char const* ptr;
};

constexpr explicit SAbc(int v)
: discriminator(1)
, value(v)
{}

constexpr explicit SAbc(char const* p)
: discriminator(2)
, ptr(p)
{}
};

// the array
constexpr SAbc abc[] =
{
SAbc(1),
SAbc("test"),
};

Frank Tetzel

unread,
Jul 10, 2016, 9:30:34 AM7/10/16
to
> I remember from GCC a syntax which was something like this:
>
> { 2, {.ptr = "test"} },
>
> But I can't figure out how to get it to work in Microsoft's C++
> compiler, and I don't know what to search for to find it via Google.

This is called designated initializers[1] and is part of the C99
standard, not in any C++ standard as far as i know. GCC allows it in
C++ code nonetheless as a GNU extension, similar to
variable-length-arrays. Clang supports it too but as Visual Studio only
has a recent C++ compiler it mostly likely does not.

Just define two overloaded ctors for the structure and use normal list
initialization.

struct SAbc
{
int discriminator;

union {
int value;
const char *ptr;
};

SAbc(int discriminator, int value)
: discriminator(discriminator), value(value) {}
SAbc(int discriminator, const char *ptr)
: discriminator(discriminator), ptr(ptr) {}
};


[1] https://gcc.gnu.org/onlinedocs/gcc-6.1.0/gcc/Designated-Inits.html

Regards,
Frank

woodb...@gmail.com

unread,
Jul 10, 2016, 12:54:21 PM7/10/16
to
I prefer your approach to Frank's, but I'd encourage
the OP to reconsider the use of the union. He may
not need it and at the least he should improve the
name of the struct -- "SAbc" doesn't cut it.

Brian
Ebenezer Enterprises - In G-d we trust.
http://webEbenezer.net

Rick C. Hodgin

unread,
Jul 10, 2016, 3:26:42 PM7/10/16
to
Brian Wood wrote:
> ... at the least he should improve the name of the struct
> -- "SAbc" doesn't cut it.

It was an example. The actual name is appropriately descriptive.

I appreciate everyone's response. I like the solutions offered.
I have a need in this project to use unions, so I need the syntax
to allow the content to be populated. If it's not possible in MSVC++,
I'll use GCC for this part and link it in. I have already done this
for another need which GCC allowed, but MSVC++ did not.
It allowed constant text to be assigned to a pointer, but in
readwrite memory, rather than readonly.

Kalle Olavi Niemitalo

unread,
Jul 10, 2016, 4:02:44 PM7/10/16
to
"Rick C. Hodgin" <rick.c...@gmail.com> writes:

> I have already done this
> for another need which GCC allowed, but MSVC++ did not.
> It allowed constant text to be assigned to a pointer, but in
> readwrite memory, rather than readonly.

Huh? Can't you do that portably:

static char readwrite[] = "some text you want";
char *pointer = readwrite;

Then assign pointer[2] = 'l' as you like.

Rick C. Hodgin

unread,
Jul 10, 2016, 5:53:08 PM7/10/16
to
It refers to this form:

http://compgroups.net/comp.lang.c++/link-object-files-from-vc++-and-gcc/2080401

By using MinGW and compiling the data and then linking to the MSVC++
project, the constant data by pointer is in readwrite memory.

Rick C. Hodgin

unread,
Jul 10, 2016, 5:54:59 PM7/10/16
to
On Sunday, July 10, 2016 at 4:02:44 PM UTC-4, Kalle Olavi Niemitalo wrote:
Here are the details I created from that reference:

https://groups.google.com/d/msg/comp.lang.c/UXGdxAzPgrg/h9NIIMAPf4kJ
0 new messages