简体   繁体   中英

Setting base object from derived class method

I have a class which stores a pointer to a data chunk and the size of the data. It implements operations like 'head', 'tail',... but it is irrelevant from the question's point of view. I use this instead of std::vector where I do not want deep copying. However I need to copy the data sometimes, so I have a member function 'duplicate' to do it.

struct ByteArray {
    char* data;
    int size;
    ByteArray(char* data, int size) : data(data), size(size) {}
    ByteArray duplicate() const {
        char *duplicatedData = new char[size];
        memcpy(duplicatedData, data, size);
        return ByteArray(duplicatedData, size);
    }
};

Now I have a derived class - extending the previous class, where I need a duplicate method too, which calls the base class' duplicate. I have managed to solve it by casting both objects to the base class, but I suspect that this is not the best solution. Am I missing a more obvious solution? Also is this class the right solution to the original problem (not having deep copy) or there is standard solution what I'm not aware of?

struct Foo : ByteArray
{
    int bar;
    ... // more members
    Foo(ByteArray &bytes, int bar) : ByteArray(bytes), bar(bar) {}
    Foo duplicate() const {
        Foo dup = *this;
        static_cast<ByteArray&>(dup) = ByteArray::duplicate();
        return dup;
    }
};

If you changed your Foo constructor to take a ByteArray by const reference instead, duplicate() would be pretty straightforward:

Foo duplicate() const {
    return Foo(ByteArray::duplicate(), bar);
}

As-is, you can still do it the same way, just need an extra line:

Foo duplicate() const {
    ByteArray ba = ByteArray::duplicate();
    return Foo(ba, bar);
}

How about something like this then...

#include <cstring>
#include <iostream>

using namespace std;

struct ByteArray {
  char* data;
  int size;
  ByteArray(char* data, int size) : data(data), size(size) {}
  void duplicate(ByteArray &toCopy) const {
    cout<<"Byte array duplicate."<<endl;
    char *data = new char[toCopy.size];
    memcpy(data, toCopy.data, size);
  }
};

struct Foo : ByteArray
{
  int bar;
  Foo(ByteArray &bytes, int bar) : ByteArray(bytes), bar(bar) {}
  void duplicate(Foo &toCopy) const {
    cout<<"Foo duplicate."<<endl;
    ByteArray::duplicate(toCopy);
  }
};

int main(){
  char* str = "some data";
  char* null = "";
  ByteArray barr (str, 9);
  ByteArray barr2 = barr;
  barr2.duplicate(barr);

  Foo farr (barr, 2);
  Foo farr2 = farr;
  farr2.duplicate(farr);

}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM