• Status: Solved
  • Priority: Medium
  • Security: Public
  • Views: 1715
  • Last Modified:

Initialize a union?

I am building a small library to do some 4d math for graphics/physics simulation. It is designed to be optimized for the altivec SIMD platform (mostly mac G4/G5).

I am trying to build a simple data type that I can use for both vector and non-vector operations, as my library evolves.

The altivec stuff is not important for this question. There is a base type called "vector float" that is a 128 bit variable, that represents 4 floats.

The defenition of my union (for a 4x4 matrix is):

typedef union {
   struct {
        vector float c0, c1, c2, c3;
    };
    float c[4][4];
    float e[16];
} AVMatrix4;

Is there any way to initialize this union with 4 vector floats.

I try:

vector float vf = {1.0f, 1.0f, 1.0f, 1.0f};
AVVector4 v = {{vf, vf, vf, vf}};

and gcc gives me "warning: aggregate has a partly bracketed initializer"
0
jukes1
Asked:
jukes1
2 Solutions
 
MercantilumCommented:
You can initialize the *first* member of the union
AVMatrix4 v = {{1.0f, 1.0f, 1.0f, 1.0f}};

(see http://www.eskimo.com/~scs/C-faq/q2.20.html)
0
 
bookiCommented:
jukes1,

To add to what Mercantilum has posted, you can also do:

vector float vf = {1.0f, 1.0f, 1.0f, 1.0f};
AVMatrix4 v = {{vf, vf, vf, vf}};

*Note: Your union is not AVVector4 but AVMatrix4.
>> AVVector4 v = {{vf, vf, vf, vf}};

b.
0
 
sunnycoderCommented:
>gcc gives me "warning: aggregate has a partly bracketed initializer"

this works fine for me ... gcc 2.96

#include <stdio.h>

typedef struct
{
        float a,b,c,d;
}vector_float;

typedef union {
           struct {
                   vector_float c0, c1, c2, c3;
                  };
            float c[4][4];
            float e[16];
} AVMatrix4;

int main ()
{
        vector_float vf = {1.0f, 1.0f, 1.0f, 1.0f};
        AVMatrix4 v = {{vf, vf, vf, vf}};
}

I think the problem is "Note: Your union is not AVVector4 but AVMatrix4." as booki noted or may be you tracked the warning down to wrong data type
0
Protect Your Employees from Wi-Fi Threats

As Wi-Fi growth and popularity continues to climb, not everyone understands the risks that come with connecting to public Wi-Fi or even offering Wi-Fi to employees, visitors and guests. Download the resource kit to make sure your safe wherever business takes you!

 
jukes1Author Commented:
booki,

You're right, its a AVMatrix4.

Sunnycoder, your code fails to compile with gcc 3.3 and my default compiler flags.

It gets a little more specific though. It still throws the aggregate warning, but it also gives me the error:

"error: cannot convert `vector_float' to `float' in initialization"

I figured out what the problem is. I am trying to initialize the structure in a C++ implementation file. When used in a C file, there are no errors or warnings.

I do not do a whole lot of mixing the languages. Can someone explain how to include and initialize the "C-style" structure in a .cpp file?
0
 
bookiCommented:
jukes1,

Problem:

    C++ does not allow for anonymous structures (no tag and no object or typedef name).  Some compilers however allow it (but only as a member of a union) as an extension to the C++ language.  The standard states that "the brace shall only contain an initializer for the first member of the union."  g++, with its extension (allowing anonymous structs in unions), implements this as the "first named member".  That is, with g++, the initializer of a union initializes the first named member.

    In AVMatrix4, the first named member is a 2-D, 4x4 array of floats 'c'.  The statement:

>>  AVMatrix4 v = {{vf, vf, vf, vf}};

therfore attempts to initialize the first row (c[0][0] ~ c[0][3]) of floats with vector_floats. Hence the error.

Solution:

Name the member.  This should compile in C++.

#include <stdio.h>

typedef struct
{
        float a,b,c,d;
}vector_float;

typedef union {
           struct {
                   vector_float c0, c1, c2, c3;
                  } a;
            float c[4][4];
            float e[16];
} AVMatrix4;

int main ()
{
        vector_float vf = {1.0f, 1.0f, 1.0f, 1.0f};
        AVMatrix4 v = {{vf, vf, vf, vf}};
}

b.
0
 
jukes1Author Commented:
Ok, that clears up a lot. I kept reading about the gcc unnamed union/structure extension, but missed the fact that initializing a union only initializes the first NAMED member, and not the first UNNAMED member.

Unfortunately, naming the member makes the union too annoying to use. Really the only reason I was trying to figure this out is because I am trying to design these couple of math classes to be optomized on my mac, and the easiest UI language to write in is objective-C.

I would prefer to just use c++ classes for this stuff, but you can't store a c++ class directly in an Objective-C structure, you can only store a pointer, and I don't like the syntax that this causes, and construction/destruction is a bit strange.

Thanks for all of the help people.
0
Question has a verified solution.

Are you are experiencing a similar issue? Get a personalized answer when you ask a related question.

Have a better answer? Share it in a comment.

Join & Write a Comment

Featured Post

Has Powershell sent you back into the Stone Age?

If managing Active Directory using Windows Powershell┬« is making you feel like you stepped back in time, you are not alone.  For nearly 20 years, AD admins around the world have used one tool for day-to-day AD management: Hyena. Discover why.

Tackle projects and never again get stuck behind a technical roadblock.
Join Now