使用模板的二维数组

时间:2011-12-22 17:11:09

标签: c++ templates dynamic-arrays

我正在尝试实现动态数组:

template <typename Item>
class Array {
private:
    Item *_array;
    int _size;
public:
    Array();
    Array(int size);
    Item& operator[](int index);
};

template <typename Item>
Array<Item>::Array() {
    Array(5);
}

template <typename Item>
Array<Item>::Array(int size) {
    _size = size;
    _array = new Item [size];

    for (int i = 0; i < size; i++)
        cout << i << " " << _array[i] << " " << &_array[i] << endl;
}

template <class Item>
Item& Array<Item>::operator[](int index) {
    if (index < 0 || index > _size-1)
        cout << "this: " << this << ". Index out of range" << endl;

    return _array[index];
}

当像这样使用时,它按预期工作,即打印5

Array< int > testArray(5);
testArray[0] = 5;
cout << testArray[0] << endl;

但是,我想将该类用于二维动态数组。我认为以下内容只是神奇地工作并打印5 ...

Array< Array<int> > testArray(5);
testArray[0][0] = 5;
cout << testArray[0][0] << endl;

......但它不起作用。当我尝试将值设置为[0] [0]时,它会崩溃。调试器显示this _size设置为0,_array设置为NULL。此时this指向最后创建的Array实例的_array的第一个元素。

我没有得到的一件事是“内部”数组调用它的构造函数。单步执行代码,我看到Array(int size)被调用一次而Array()被调用五次。我想创建具有特定大小的内部数组,但使用Array< Array<int>(10) > testArray(5)不能编译。

您能否就此提供一些见解?似乎我还不能完全围绕模板...

3 个答案:

答案 0 :(得分:6)

您无法在C ++中链接构造函数调用。您的第一个构造函数实现什么都不做,因此父Array中包含的5个实例最终未初始化,导致未定义的行为。

要修复,您可以将默认值添加到另一个构造函数的size参数,或者在单独的(私有)函数中分解初始化逻辑,并从两个构造函数中调用它。

编辑:第一个构造函数无效的原因是该行

Array(5)

不会调用当前实例的构造函数,而是分配一个新的(未命名的)临时Array实例,该实例会在行尾立即销毁。

答案 1 :(得分:3)

使用构造函数的默认值来调用它而不需要参数,即Array(int index = 5);

请检查一下: http://www.parashift.com/c++-faq-lite/ctors.html#faq-10.3

类的一个构造函数可以调用同一个类的另一个构造函数来初始化这个对象吗?

答案 2 :(得分:1)

您无法从默认的ctor中拨打其他ctor。如果您想拥有默认值,可以将两者合并为一个。

template <typename Item>
Array<Item>::Array(int size = 5) {
    _size = size;
    _array = new Item [size];

    for (int i = 0; i < size; i++)
        cout << i << " " << _array[i] << " " << &_array[i] << endl;
}

但是如果您仍然希望拥有两个ctor,那么您可以将实现移动到可以从这两个中使用的private _setup函数。

template <typename Item>
Array<Item>::Array() {
    _setup(5);
}

template <typename Item>
Array<Item>::Array(int size) {
    _setup(size);
}

template <typename Item>
void Array<Item>::_setup(int size) {
    _size = size;
    _array = new Item [size];

    for (int i = 0; i < size; i++)
        cout << i << " " << _array[i] << " " << &_array[i] << endl;
}

已修改为新建数组删除无效的初始值设定项。