Search code examples
c++c++11const-reference

reference-to-cont class member initialized with non-const value


I have a class that should, as its input data, either use a reference to external data (without copying), or create the data itself based on other input. I prefer using references (to avoid dereferencing, since the data are matrices) and ended up with the following structure (simplified):

#include <iostream>
#include <vector>
using namespace std;
using VectI = vector<int>;

class A {
    VectI x0;
    VectI const & x = x0;
public:
    A(VectI const & extX) : x(extX) {}     // referencing existing external data
    A(int i) { x0.push_back(i); x0.push_back(i*i); }   // create from other data
    void show_x()
        { cout << "x ="; for (auto&& i : x) cout << " " << i; cout << endl; }
};

int main() {
    VectI myX = {1, 2, 3};
    A a(myX); a.show_x(); // a references myX
    A b(2); b.show_x();   // b creates its own data based on i=2
    return 0;
}

The example works:

x = 1 2 3
x = 2 4

but are there any potential problems with this approach? In particular, is the fact that I am changing x0 that is referenced by the const vector x 'legal' C++, or is it something that other compilers might complain about?

Also, can I be sure that the first constructor avoids copying data?


Solution

  • This is fine in the C++11 standard but your code is very brittle.

    In particular the compiler generated copy and move constructors and the assignment operator will not work correctly, so you'll have to build your own.

    You might also encounter dangling references: remember that the object lifetime extension due to a const reference is not transitive. The behaviour on using A(VectI const & extX) with an anonymous temporary is undefined.

    Using a pointer to VectI - perhaps even a std::unique_ptr to a VectI along with a concept of ownership might be a safer way to go.