3

Here's a weird issue I'm facing - probably something ultra-basic given my rusty C++ skills but I'm still perplexed :

  • I've got a class
  • We've also got an array of unsigned long longs in this class - let's call that arr

My Class Interface :

typedef unsigned long long U64;

class DQClass
{
    public:
        DQClass (void);
        virtual ~DQClass (void);

        U64 arr[12];
};

Now as for the implementation...

Test 1 (This works) :

DQClass::DQClass (void)
{
        this->arr[0] = 0x8100000000000000ULL;
        this->arr[1] = 0x4200000000000000ULL;

        // and so on..
}

Test 2 (This doesn't) :

DQClass::DQClass (void)
{
    this->arr = 
    {
        0x8100000000000000ULL,
        0x4200000000000000ULL,
        0x2400000000000000ULL,
        0x1000000000000000ULL,
        0x0800000000000000ULL,
        0x00FF000000000000ULL,
        FLIPV(0x8100000000000000ULL),
        FLIPV(0x4200000000000000ULL),
        FLIPV(0x2400000000000000ULL),
        FLIPV(0x1000000000000000ULL),
        FLIPV(0x0800000000000000ULL),
        FLIPV(0x00FF000000000000ULL)
    };
}

Error :

dqclass.cpp: In constructor ‘DQClass::DQClass()’:
dqclass.cpp:28: error: expected primary-expression before ‘{’ token
dqclass.cpp:28: error: expected `;' before ‘{’ token

Why isn't this working? Shouldn't it be working in the same fashion as, e.g. U64 someArr[12] = {0,1,2,3,4,5,6,7,8,9,10,11} would?

Any ideas?

Dr.Kameleon
  • 22,532
  • 20
  • 115
  • 223

1 Answers1

6

Arrays can't be assigned like that (or any other way), only initialized:

 // sorry for bad formatting
DQClass::DQClass (void)
: arr(
    {
        0x8100000000000000ULL,
        0x4200000000000000ULL,
        0x2400000000000000ULL,
        0x1000000000000000ULL,
        0x0800000000000000ULL,
        0x00FF000000000000ULL,
        FLIPV(0x8100000000000000ULL),
        FLIPV(0x4200000000000000ULL),
        FLIPV(0x2400000000000000ULL),
        FLIPV(0x1000000000000000ULL),
        FLIPV(0x0800000000000000ULL),
        FLIPV(0x00FF000000000000ULL)
    }) {
}

Use constructor initialize list.


You could also use std::array:

std::array<U64, 12> arr;

// ...

this->arr = 
    {{
        0x8100000000000000ULL,
        0x4200000000000000ULL,
        0x2400000000000000ULL,
        0x1000000000000000ULL,
        0x0800000000000000ULL,
        0x00FF000000000000ULL,
        FLIPV(0x8100000000000000ULL),
        FLIPV(0x4200000000000000ULL),
        FLIPV(0x2400000000000000ULL),
        FLIPV(0x1000000000000000ULL),
        FLIPV(0x0800000000000000ULL),
        FLIPV(0x00FF000000000000ULL)
    }};
Pubby
  • 51,882
  • 13
  • 139
  • 180
  • I'm not really sure what you're trying to say in your first piece of code... Could please explain to me why `U64 someArr[12] = {0,1,2,3,4,5,6,7,8,9,10,11}` **does** work? – Dr.Kameleon Dec 13 '12 at 08:24
  • 3
    @Dr.Kameleon Initialization is different from assignment. Arrays have silly behavior and so I can't give you a good reason why arrays can't be assigned. Just use `std::array` for such purposes. – Pubby Dec 13 '12 at 08:26
  • 1
    @Dr.Kameleon Maybe this will help http://stackoverflow.com/questions/3437110/why-does-c-support-memberwise-assignment-of-arrays-within-structs-but-not-gen – Pubby Dec 13 '12 at 08:28
  • OK, here's another interesting issue : I decided to try the `std::array` way. While trying `#include `, I'm getting `error: array: No such file or directory` and `ISO C++ forbids declaration of ‘array’ with no type`. (Hint : using `g++` in Mac OS X 1.6.8) – Dr.Kameleon Dec 13 '12 at 08:31
  • 1
    @Dr.Kameleon You need a fairly recent version that supports C++11. You could also try `boost::array` which is what `std::array` is based off of. – Pubby Dec 13 '12 at 08:33
  • Yep, that's exactly what I was thinking right now. I'm making fairly extensive use of Boost anyway, so it will do no harm... Thanks a lot for your help, buddy! ;-) – Dr.Kameleon Dec 13 '12 at 08:34
  • @Dr.Kameleon: Include `` and add the flag `-std=c++0x`. If you're not using a C++11 compiler, the code in Pubby's answer won't work even with `boost::array`. – Benjamin Lindley Dec 13 '12 at 08:36
  • @BenjaminLindley Still comes with an error : `cc1plus: error: unrecognized command line option "-std=c++0x"` – Dr.Kameleon Dec 13 '12 at 08:39
  • @BenjaminLindley Note that `g++ --version` gives : `i686-apple-darwin10-llvm-g++-4.2 (GCC) 4.2.1 (Based on Apple Inc. build 5658) (LLVM build 2336.1.00)` – Dr.Kameleon Dec 13 '12 at 08:40
  • @Dr.Kameleon If you are not using C++11 you are missing out. Upgrade 4.7 or latest Clang if you can. (I realize this is not always possible) – Pubby Dec 13 '12 at 08:41
  • @Dr.Kameleon: You're out of luck then, unless you can update your compiler. – Benjamin Lindley Dec 13 '12 at 08:41
  • @BenjaminLindley+Pubby OK, guys! Thanks a lot for your help! It's been some time that I've been working full-time with Objective-C code that I've forgotten what it is to be working with C++ and I keep thinking it's always my fault... lol Guess I'll have to see what I can do with upgrading the compiler, then. Thanks, again! :-) – Dr.Kameleon Dec 13 '12 at 08:44