1

按照网上教程中关于5的规则的例子,我写了这个类:

#include <iostream>
#include <cstring>
#include <utility>
class A2
{
    char* _buff;
public:
    A2(const char *text = "test") {
        std::cout << "New A2\n";
        _buff = new char[256];
        size_t length = strnlen(text, 255) + 1;
        strncpy(_buff, text, length);
    }
    
    virtual ~A2() {
        std::cout << "Delete A2\n";
        delete[] _buff;  // deallocate
    }
    
    A2(const A2& other) : A2(other._buff) {
        std::cout << "Copy constructor A2\n";
    }
    
    A2(A2&& other) noexcept : _buff(std::exchange(other._buff, nullptr)) {
        std::cout << "Move constructor A2\n";
    }
    
    A2& operator=(const A2& other) {
        std::cout << "Copy assignment A2\n";
        return *this = A2(other);
    }
    
    A2& operator=(A2&& other) noexcept {
        std::cout << "Move assignment A2\n";
        std::swap(_buff, other._buff);
        return *this;
    }
};

并且做一些测试它实际上似乎对我有用(它是通过示例中的一些自定义复制的)。

所以我尝试创建一个继承自 A2 的类(在这种情况下,作为构造函数参数的文本也传递给父级,但在它们的内部管理中它们保持独立):

class B2 final : public A2
{
    char* _buff2;
public:
    B2(const char* text) : A2(text) {
        _buff2 = new char[256];
        size_t length = strnlen(text, 255) + 1;
        strncpy(_buff2, text, length);
        std::cout << "new B2\n";
    }

    ~B2() {
        std::cout << "delete B2\n";
        delete[] _buff2;  // deallocate
    }
    
    B2(const B2& other) : A2(other) {
        _buff2 = new char[256];
        size_t length = strnlen(other._buff2, 255) + 1;
        strncpy(_buff2, other._buff2, length);
        std::cout << "copy constructor B2\n";
    }
    
    B2(B2&& other) noexcept  : A2(static_cast<A2&&>(other)), _buff2(std::exchange(other._buff2, nullptr))
    {
        std::cout << "move constructor B2\n";
    }
    
    B2& operator=(const B2& other) {
        std::cout << "operator = in B2\n";
        A2::operator= (other);
        size_t length = strnlen(other._buff2, 255) + 1;
        strncpy(_buff2, other._buff2, length);
        return *this;
    }
    
    B2& operator=(B2&& other) noexcept {
        std::cout << "move assignment B2\n";
        A2::operator=(static_cast<A2&&>(other));
        std::swap(_buff2, other._buff2);
        return *this;
    }
};

它似乎工作正常(我也在这里做了一些测试,并检查了调试器是否一切正常)。

但我的疑问是:为 B2 课写的内容是否正确?我不太相信直接使用运算符(A2::operator = (other)并将A2::operator = (static_cast <A2&&> (other)))参数传递给父级。

有什么方法可以更清晰、更正确地编写相同的代码?

4

0 回答 0