2

我有一个项目类,这实际上是一个 int 的包装器。我有一个模板化的节点类。我将项目类作为模板参数传递给它。

我想创建一个模板节点类的数组,但编译器不喜欢它。当我使用相同的语法创建单个对象时,它可以工作。为什么不能推导出数组元素来初始化模板类的数组?创建模板类的对象数组的正确方法是什么?

Heres item 类,它是一个int.

using namespace std;

class bItem {
private :     
    int item{INT_MIN};
public:
    bItem() : item(INT_MIN) {}
    bItem(int val) : item(val) {}
    int getItem() { return item; }
    bItem operator==(const bItem& val) {
        return item == val.item;
    }
    bItem operator>(const bItem& val) {
        return item > val.item;
    }
    bItem operator<(const bItem& val) {
        return item < val.item;
    }
    friend ostream& operator<<(ostream& os, const bItem& item) {
        os << "value:" << item.item << endl;
        return os;
    }
};

这是模板化的节点类

#include <iostream>
using namespace std;
template<class itemType>
class bNode {
    itemType item{};
    bNode* prev{};
    bNode* next{};
public:
    bNode() : item(), prev(nullptr), next(nullptr) {}
    bNode(itemType _item) : item(_item), prev(nullptr), next(nullptr) {}
    ~bNode() {
        delete prev;
        delete next;
    }
    
    friend ostream& operator<<(ostream& os, const bNode& node) {
        os << "node " << node.item<< endl;
        return os;
    }
};

继承人main()

int main()
{    
    bNode<bItem> nodes[5]{ 1,2,3,4,5 }; //this does not compile
    bNode<bItem> node2(6); //this compiles ok

}

这是错误消息

error C2440: 'initializing': cannot convert from 'int' to 'bNode<bItem>'
message : No constructor could take the source type, or constructor overload resolution was ambiguous
4

1 回答 1

4

在数组的聚合初始化中,元素是从初始化列表的相应子句复制初始化的。这意味着具有 type 的元素bNode<bItem>需要从 复制初始化int,这需要两个用户定义的隐式转换, from inttobItem和 from bItemto bNode,这是不允许的。

每个direct public base, (since C++17)数组元素或非静态类成员,按照类定义中数组下标/外观的顺序,从初始化列表的相应子句复制初始化。

作为解决方法,您可以对隐式转换的时间施加限制,例如

bNode<bItem> nodes[5] = { bItem(1),bItem(2),bItem(3),bItem(4),bItem(5) };

或者你可以添加另一个构造函数intbNode然后它也可以被复制初始化int

// forward it to bNode::bNode(itemType)
bNode(int val) : bNode(itemType(val)) {}

BTW:bNode<bItem> node2(6);执行直接初始化,只需要一次隐式转换(从intbItem),转换bItme后的传递给构造bNode函数node2。它没有复制初始化等问题。(复制初始化bNode<bItem> node2 = 6;也不起作用。)

此外,复制初始化中的隐式转换必须直接从初始值设定项生成 T,而直接初始化需要从初始值设定项到 T 构造函数的参数的隐式转换。

于 2020-09-01T02:15:23.403 回答