Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Cast pointer to fixed-size array in return statement

Tags:

c++

arrays

The simplest way to ask this question is with some code:

struct Point
{
    int x;
    int y;
    int z;

    int* as_pointer() { return &x; }        // works
    int (&as_array_ref())[3] { return &x; } // does not work   
};

as_pointer compiles, as_array_ref does not. A cast seems to be in order but I can't figure out the appropriate syntax. Any ideas?

like image 906
Ben Hymers Avatar asked Apr 25 '13 10:04

Ben Hymers


3 Answers

I find that array types are easier to deal with with a typedef:

typedef int ints[3];

Then your as_array_ref must be written so that &as_array_ref() == &x.

The following syntaxes are possible:

  1. plain C-style cast from int* to ints*:

    ints& as_array_ref() { return *( (ints*)(&x) ); }

  2. C++ style reinterpret_cast (suggested by @Mike Seymour - see also his answer). It is often considered a better practice in C++:

    ints& as_array_ref() { return *reinterpret_cast<ints*>(&x); }

  3. Cast from int& to ints& which is slightly shorter but (for me) less intuitive:

    ints& as_array_ref() { return reinterpret_cast<ints&>(x); }

like image 193
Antoine Avatar answered Oct 12 '22 08:10

Antoine


The cast you need to reinterpret a reference to a variable as a reference to an array is:

reinterpret_cast<int(&)[3]>(x);

Be aware that using this gives undefined behaviour; it will probably work on any sensible implementation, but there's no guarantee that there won't be padding between the members of the class, while arrays are not padded.

like image 25
Mike Seymour Avatar answered Oct 12 '22 07:10

Mike Seymour


I think that what you're trying to do would be easier (and clearer/cleaner) with an union.

like image 42
Nico Brailovsky Avatar answered Oct 12 '22 07:10

Nico Brailovsky