0

I wrote these apparently harmless lines inside my code just for naming convenience:

struct Foo{
    double vec[2];
    double& a=vec[0],b=vec[1];
};

But for some reason the variable "a" works fine and "b" does not ( it returns garbage). This is strange since it seemed to be a valid way to declare them. I then tested some alternate ways to do it:

#include <iostream>
using namespace std;
struct Foo{
    double vec[2];
    double& a=vec[0],b=vec[1]; //does not work

    double& c=vec[0];
    double& d=vec[1]; //works

    double ev,fv;
    double& e=ev,f=fv; // does not work

    double& g,h; // does not work
    Foo() : g(vec[0]) ,h(vec[1]){};

    void bar(){
        vec[0]=1;
        vec[1]=2;
        ev=1;
        fv=2;
        cout<<"a: "<<a<<endl;
        cout<<"b: "<<b<<endl;    
        cout<<"\nc: "<<c<<endl;
        cout<<"d: "<<d<<endl;
        cout<<"\ne: "<<e<<endl;
        cout<<"f: "<<f<<endl;        
        cout<<"\ng: "<<g<<endl;
        cout<<"h: "<<h<<endl;

        double& i=vec[0], j=vec[1]; //works
        cout<<"\ni: "<<i<<endl;
        cout<<"j: "<<j<<endl;
    }
};

int main(int, char **) {
    Foo X;
    X.bar();

    double vec[2];
    vec[0]=1;
    vec[1]=2;
    double& k=vec[0],l=vec[1];//works
    cout<<"\nk: "<<k<<endl;
    cout<<"l: "<<l<<endl;
}

In summary, the pairs (a,b), (e,f) and (g,h) don't work properly in the same way (i.e. the second variable returns some garbage). I know this could be easily avoided by writing like (c,d), but this whole behaviour is puzzling, specially because (a,b) fails while (i,j) and (k,l) work, even though the main difference seems to be where the declaration takes place. Why is that so?

Note: C++11 standard. Using -pedantic -Wall -Wextra in g++ did not throw any warnings

Community
  • 1
  • 1
guivenca
  • 149
  • 1
  • 11
  • The side where you write the `&` is misleading, the `&` in reference declarations (as the `*` in pointer declarations) groups with the variable name, not with the type. – Matteo Italia Sep 28 '15 at 22:07
  • Declaring pointers and references in the same line is asking for trouble. Better avoid it altogether. – juanchopanza Sep 28 '15 at 22:08
  • @juanchopanza This type of common mistake is one reason I advocate one declaration per line regardless of type. In addition, it makes commenting on said declaration easier. – Casey Sep 28 '15 at 22:17

2 Answers2

7
double& a=vec[0],b=vec[1];

is the same as:

double& a=vec[0];
double b=vec[1];

You can use:

double& a=vec[0], &b=vec[1];

or, preferably:

double& a=vec[0];
double& b=vec[1];
R Sahu
  • 200,579
  • 13
  • 144
  • 260
  • So it seems the ones who failed did so because they were doubles(not references) and received the garbage that was initially in vec. Thanks – guivenca Sep 28 '15 at 22:22
4

As for pointers, putting the & before the space or after it, is not changing anything.

This will work:

double &a=vec[0],&b=vec[1];

and also this will work:

double& a=vec[0], &b=vec[1];

the first & goes only for a the second for b

SHR
  • 7,570
  • 9
  • 36
  • 56