1

I am new to c++ and got really confused about this class of numerical array I am trying to implement. I hope somebody can give me some advice:

class ndarray {
public:
double *data;
...
ndarray(...) { \* code to dynamically allocate data *\}
ndarray(const ndarray& A) { \* code to copy construct *\}
~ndarray() { \* code to delete data *\};

ndarray& operator=(const ndarray& A) {\* code to deep copy *\}

friend ndarray& log(const ndarray& A) { 
    ndarray B(...); 
    \* code to popularize B[i] with log(A[i])  *\
    return B; }
};
int main() {
    ndarray A(...), B(...);
    B=log(A);
}

Here I overloaded the = operator to deep copy the data elements. After inserting some outputs to the code I found that the B=log(A) code has called the = operator explicitly by creating and popularizing a new data array elementwise, even though the overloaded log function returns by reference. My question is, how can I avoid this extra copying of data elementwise and use the ndarray object created by log function directly. Obviously the compiler is not helping me in this case.

user138668
  • 161
  • 4
  • 3
    Returning a reference to a local variable is broken (a good compiler will print a warning). I think you want to read up on return value optimization and rvalue references (aka move semantics). Also, std::valarray might fit your needs (it uses a more complicated expression template mechanism to reduce copying). – Marc Glisse Sep 10 '16 at 10:14
  • Thanks for pointing out the return by reference a local variable issue. Somehow the compiler (visual c++ 2012) did not complain. The code runs as if it returns by value. The question remains on how to avoid copy of the returned value element-wise. If I overload the ``=`` operator without deep copy, my code crashes at the end when these objects are being destructed. That I don't understand, since the ``log(A)`` call created the array and assigned the pointer only to ``B.data``. Upon destruction, why should it crash? Also the ``std::valarray`` class seems obsolete. – user138668 Sep 10 '16 at 10:41
  • @πάνταῥεῖ A hasty decision, because the question of "how can I avoid this extra copying of data elementwise and use the ndarray object created by log function directly." is not answered by the linked. – Adrian Colomitchi Sep 10 '16 at 11:11
  • @user138668 _"The question remains on how to avoid copy of the returned value element-wise."_ Use an output parameter passed by reference. – πάντα ῥεῖ Sep 10 '16 at 11:13
  • @AdrianColomitchi Vote to reopen the question, if you think the decision was wrong. – πάντα ῥεῖ Sep 10 '16 at 11:14
  • @user138668 - "how can I avoid this extra copying of data elementwise" Answer: in C++0x and , you need to look for ['move constructible/assignable'](http://stackoverflow.com/questions/3106110/what-are-move-semantics) – Adrian Colomitchi Sep 10 '16 at 11:16
  • @πάνταῥεῖ It's a duplicate all-right - except that the linked by itself doesn't answer to his question of "How to avoid copying". – Adrian Colomitchi Sep 10 '16 at 11:20
  • Thank you for all your comments. I now more or less understand, that I need to dig into the "move constructor" and "move assignment" concepts. – user138668 Sep 10 '16 at 13:04

0 Answers0