C++对象数组的初始化

如果一个类有默认的构造函数,使用new动态实例化一个对象数组不是件难事,如下代码:

class animal
{
public:
    animal():num(0)
    {}
    ~animal()
    {}
private:
    int num;
};

Animal *ani = new Animal[5];
delete[]ani;

然而 new Obj[n]的形式仅仅适用于不需传入实参的默认构造函数,否则编译器报错。想要初始化对象数组的同时指定各个构造函数的参数,有以下几种解决途径:

1.若初始化对象数组时已知其size,使用诸如 new Obj[n]{(),(),...()} 的形式,大括号内每个小括号对应每个对象的构造函数参数:

class Array1D
{
public:
	Array1D(int len2)
		:len2D(len2)
	{
		plist = new T[len2];
		for (int i = 0; i < len2; i++)
			plist[i] = static_cast<T>(0);
	}
	~Array1D()
	{
		if (nullptr != plist)
			delete[] plist;
	}
private:
	T* plist;
	int len2D;
};

pArray1D = new Array1D[2]{(1),(2)}

 

2.若初始化对象数组时未知其size,需要把分配内存和构建对象的动作分开。可借助C++11的allocator。先使用allocate分配内存并用指针记录这块空间;然后用construct方法对指针所指向内存进行对象构建;当然不再使用对象时用destory方法析构对象;注意,既然分配内存和构建对象动作已分开,那么析构对象和释放内存也要配对,用deallocate释放内存:

class Array2D
{
public:
    //class Array1D
    class Array1D
    {...};

    //Array2D
    Array2D(int len1, int len2)
        :len1D(len1)
    {
        pArray1D = alloc.allocate(len1);
        for (int i = 0; i < len1; i++) {
            alloc.construct(pArray1D + i, len2);
        }
    }
    ~Array2D()
    {
        for (int i = 0; i < len1D; i++) {
            alloc.destroy(pArray1D + i);
        }
        alloc.deallocate(pArray1D, len1D);
    }

private:
    Array1D* pArray1D;
    int len1D;
    allocator<Array1D> alloc;
};

 

3.使用operator new和placement new,与allocator原理类似,分四步走:

class animal
{
public:
    animal():num(0)
	{}
    animal(int _num):num(_num)
    {}
    ~animal()
    {}

    void show() {
        cout << num << endl;
    }

    void* operator new(size_t size, void* p)
    {
        return p;
    }
private:
    int num;
};

int main(int argc, char* argv[])
{
    {
        // operator new
        void* p = operator new(5 * sizeof(animal));
        animal* a = static_cast<animal*>(p);
        // placement new, constructor
        for (int i = 0; i < 4; i++)
        {
            new(a + i) animal(i);
        }
        new(a + 4) animal;
        // use
        for (int i = 0; i < 5; i++) {
            (a + i)->show();
        }
        // destructor
        for (int i = 0; i < 5; i++) {
            (a + i)->~animal();
        }
        // delete
        delete[] p;
    }
    return 0;
}

参考:https://www.cnblogs.com/SimonKly/p/7819147.html

  • 6
    点赞
  • 44
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值