繁体   English   中英

C++ 在构造函数中使用数组初始化 object

[英]C++ Initiating object with array in constructor

我正在尝试使用数组启动 object。 有没有办法用指针来做,或者我应该找到另一种方法来做到这一点。

编辑:我想用动态 memory 分配来编写这段代码,我知道向量是解决这个问题的更好方法。

#include <iostream>

template <class t>
class die {
private:
    int sideCount;
    t* valueOfSides;
public:
    die(int side, t arr[]) {
        sideCount = side;
        valueOfSides = (t*)malloc(side * sizeof(t));
        for (int counter; counter < side; counter++) {
            valueOfSides[counter] = val[counter];
        }
    }

    ~die() {
        free(valueOfSides);
    }
};

int main() {
    die<int> sixsided(6, {1,2,3,4,5,6});
} 

正确的方法是

std::vector<t> valueOfSides;

template<size_t len> die(t (&arr)[len])
: valueOfSides(std::begin(arr), std::end(arr))
{}

或者

std::vector<t> valueOfSides;

die(std::initializer_list<t> arr) : valueOfSides(arr) {}

我认为。 虽然真的,最好的答案是

std::vector<t> valueOfSides;

die(std::vector<t> arr) : valueOfSides(std::move(arr)) {}

永远不要在 C++ 中使用原始指针来拥有 memory ,并且几乎永远不要使用newmalloc 实际上,由于滥用malloc ,您的代码中有未定义的行为。


如果您绝对疯了,或者正在做作业,则可以使用原始指针来完成,尽管我怀疑我是否可以在没有测试和编译器的情况下完全正确。

template<class t>
class die {
private:
    int sideCount;
    t* valueOfSides;
public:
    die(int side, t* arr) {
        sideCount = 0;
        std::size_t buffer_size = sizeof(t)*side;
        char* buffer;
        try {
            buffer = new char[side];
            valueOfSides = reinterpret_cast<t*>(buffer);
            for(int i=0; i<side; i++) {
                new(valueOfSides+i)t(arr[i]);
                sideCount++;
            }
        } catch(...) {
            for(int i=sideCount; i>=0; i--)
                (valueOfSides+i)->~t();
            delete[]buffer;
            throw;
        }
    }
    die& operator=(die&& rhs) {
        sideCount = rhs.sideCount;
        valueOfSides = rhs.valueOfSides;
        rhs.valueOfSides = nullptr;
        rhs.sideCount = 0;
        return *this;
    }
    //die& operator=(const die& rhs) not shown because its super hard.

    ~die() {
        for(int i=sideCount; i>=0; i--)
            (valueOfSides+i)->~t();
        delete[]reinterpret_cast<char*>(valueOfSides);
    }
};

正如我们之前所说,把这些东西做好是非常困难的。 使用std::vector

使用std::vector

#include <iostream>
#include <initalizer_list>
#include <vector>

template<class T>
class die {
public:
    die() = default;
    die(std::initializer_list<T> list)
    : sides{list}
    { /* DO NOTHING */ }
private:
    std::vector<T> sides{};
};

int main() {
    die<int> sixsided({1,2,3,4,5,6});
} 

使用更多的 C 技术可以做到这一点的一种方法是变量参数列表:

#include <cstdarg>
#include <iostream>

template <class t>
class die {
private:
    int sideCount;
    t* valueOfSides;
public:
    die(int side, ...) {
        sideCount = side;
        valueOfSides = new t[side];

        va_list args;
        va_start(args, side);
        for (int counter = 0; counter < side; counter++) {
            valueOfSides[counter] = va_arg(args, t);
        }
        va_end(args);
    }

    ~die() {
        delete[] valueOfSides;
    }
};

int main() {
    die<int> sixsided(6, 1,2,3,4,5,6);
}

不是传递数组,而是单独传递参数(即不需要临时数组)并使用va_list来访问它们。

此外,对mallocfree的调用被替换为newdelete ,这是 C++ 分配和释放 memory 的方式。

C++ 解决方案:


template <class t>
class die {
private:
    int sideCount;
    t* valueOfSides;
public:
    die(int side, t arr[]) {
        sideCount = side;
        valueOfSides = new T[side]
        for (int counter = 0; counter < side; counter++) { //always initialize variables
            valueOfSides[i] = arr[i];
        }
    }

    ~die() {
        delete[] valueOfSides;
    }
};

int main() {
    int arr[6] = { 1,2,3,4,5,6 };
    die<int> sixsided(6, arr);
}

new的运算符就像mallocdeletedelete[]运算符就像free 它们是动态分配器。

C 解决方案:

template <class t>
class die {
private:
    int sideCount;
    t* valueOfSides;
public:
    die(int side, t arr[]) {
        sideCount = side;
        valueOfSides = (t*)malloc(side * sizeof(t));
        for (int counter = 0; counter < side; counter++) { //always initialize variables
            valueOfSides[i] = arr[i];
        }
    }

    ~die() {
        free(valueOfSides);
    }
};

int main() {
    int arr[6] = { 1,2,3,4,5,6 };
    die<int> sixsided(6, arr);
}

注意:在 C 中, <iostream> header 将不起作用,这仅是 C++。

还有其他容器,即std::vector可以工作,但这是您的答案的解决方案。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

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