使用没有默认构造函数的类/类型初始化自定义容器

initializing custom container with class/type that has no default constructor

本文关键字:类型 初始化 自定义 默认 构造函数      更新时间:2023-10-16

如何将容器初始化为没有默认值的类?如何在不使用 new 或调用类的默认构造函数的方法的情况下创建所需的指针数组?

#include <string>
#include <iostream>
#include <vector>
#include "MyVector.h"
class NoDefault {
 public:
  //NoDefault():value(0){};
 NoDefault(const int& value) : value(value) {}
  int value;
};
std::ostream& operator<<(std::ostream& out, const NoDefault& noDefault) {
  out << noDefault.value;
  return out;
}
int main() {
  MyVector<int> intVec(10, 99);
  MyVector<std::string> stringVec(5, "hi");
  MyVector<NoDefault> noDefaultVec(4, -3);
  std::vector<std::vector<std::string>> tempRealVec({{"hi", "bye"}, {"sly", 
"guy", "why"}});
  MyVector<MyVector<std::string> > tempMyVec(tempRealVec);
  MyVector<MyVector<MyVector<std::string> > > vecVecVecStringVec(2, tempMyVec);
  std::cout << "intVec = " << intVec << std::endl;
  std::cout << "stringVec = " << stringVec << std::endl;
  std::cout << "noDefaultVec = " << noDefaultVec << std::endl;
  std::cout << "vecVecVecStringVec = " << vecVecVecStringVec << std::endl;
  std::cout << "hello" << std::endl;
  return 0;
}

这是构造函数

template <typename T>
MyVector<T>::MyVector(const unsigned int& numElements,const T& value):data_(new 
T[numElements]),size_(numElements)
{
    for(int i = 0; i < size_; i++)
    {
        if(std::is_same<T,int>::value)
            data_[i]=T(value);
        else if(std::is_same<T,std::string>::value)
            data_[i]=T(value);
        else if(std::is_same<T,MyVector>::value)
            data_[i]=T(value);
        else if(std::is_same<T,NoDefault>::value)
            data_[i]=T(value);
    }
}

由于在初始值设定项列表中使用 new 而引发的错误是调用 NoDefault::NoDefault(( 的匹配函数,即使我创建了该构造函数,也会破坏目的。然后,它使用默认值打印向量,而不是在调用 MyVector 时作为第二个参数给出的值。

您可以使用

放置new。 放置new允许您在特定内存位置构造对象,因此步骤如下所示:

  1. 分配原始内存(malloc::operator new两者都有效(
  2. 在此原始内存中构造对象 ( new (ptr) NoDefault{args} (

这大致就是常规new的工作方式(通过::operator new分配内存,然后使用放置new来构造对象(。 我不确定是否需要像vector这样的 stdl 容器使用这种方法,但如果它们不这样做,我会有点惊讶。

最大的警告(这是一个很大的警告(是,在使用放置new时,您必须手动调用析构函数(我唯一知道您有意调用析构函数的时间(。 调用析构函数后,您可以使用适当的方法(例如,free::operator delete(自由释放分配的内存。

有关详细信息,请参阅

C++常见问题解答。