nekitip
nekitip

Reputation: 365

when a class element from array is modified, it behaves like it is a copy, not reference

This is a simple thing that I'm not sure if it is possible in C++ like in some other languages. The thing behaves like it is a copy, but not the same object. I would expect that if this was struct, or some other value type - this would be expected behaviour, but for class, I expected this to behave like I'm looking at "reference", that is - the same object as is in array. What am I doing wrong?

// Example program
#include <iostream>
#include <string>


class someclass
{
    public:        
    void setn(int n2);
    int n=10;
};

void someclass::setn(int n2){
    n=n2;
};


int main()
{
  someclass moreofthem[5];   
  someclass my=moreofthem[1];  
  std::cout << "start value: " << my.n << " as inital\n"; //10
  my.setn(2);  
  std::cout << "new value: " << my.n << " as expected\n"; //2
  std::cout << "value in list: " << moreofthem[1].n << " why?\n";  //10?

}

Upvotes: 1

Views: 65

Answers (3)

Sergey Kalinichenko
Sergey Kalinichenko

Reputation: 726509

Unlike C#, C++ makes no distinction between a struct and a class. In fact, the two are completely interchangeable, and follow value semantic.

Fortunately, C++ also provides references and pointers as language constructs, which let you deal with references to instances of classes and structures:

 someclass moreofthem[5];   
 someclass& my = moreofthem[1];  
 //       ^
 //   That's it! Now you have yourself a reference
 std::cout << "start value: " << my.n << " as inital\n"; //10
 my.setn(2);

or if you prefer pointers

 someclass moreofthem[5];   
 someclass* my = &moreofthem[1];  
 //       ^      ^
 //   declare and use a pointer; note -> below
 std::cout << "start value: " << my.n << " as inital\n"; //10
 my->setn(2);

Unlike C#, where a class ensures that instances are handled through references (which represent a mix between C++ references and C++ pointers) C++ lets you decide how you want to handle your instances - by value, by reference, or by pointer. The behavior is close to C#'s ref parameter passing for objects of value type, but it is available in all contexts, including instance and local variables. This gives you more flexibility to handle the same object through a reference or by value in different contexts.

Upvotes: 5

sjsam
sjsam

Reputation: 21965

I would expect that if this was struct, or some other value type - this would be expected behaviour, but for class, ...

The keywords class and struct can be used interchangeably. The only difference is that, if you don't specify an access modifer the default would be :

  • public in struct
  • private in class

That said,

someclass& my=moreofthem[1]; 

makes a reference and that is what you're looking for. Here the reference my acts like an alias of the original variable moreofthem[1]

Upvotes: 3

Some programmer dude
Some programmer dude

Reputation: 409166

That's because the object my is a copy of moreofthem[1], not a reference.

If you want a reference you need to use the ampersand when defining the variable:

someclass& my=moreofthem[1];  
//       ^
// Note ampersand here

Upvotes: 4

Related Questions