如何在 C++ 类中初始化可变大小数组?
Posted
技术标签:
【中文标题】如何在 C++ 类中初始化可变大小数组?【英文标题】:How do I initialize a variable size array in a C++ class? 【发布时间】:2014-11-29 15:21:13 【问题描述】:我有一个类需要存储一个可变大小的数组。理想情况下,这个大小将被定义为给类的构造函数的参数。
我可以定义一个常量,然后使用它,如下所示:
#include <iostream>
#define ARRSIZE 5
class Classy
private:
int myarray[ARRSIZE];
public:
Classy();
void printarray();
;
Classy::Classy()
for(int i = 0; i < ARRSIZE; i++)
myarray[i] = i * i * 2;
void Classy::printarray()
for(int i = 0; i < ARRSIZE; i++)
std::cout << myarray[i] << std::endl;
但是,我想这样做:
#include <iostream>
class Classy
private:
int arraysize;
int myarray[arraysize];
public:
Classy(int parraysize);
void printarray();
;
Classy::Classy(int parraysize)
arraysize = parraysize;
for(int i = 0; i < arraysize; i++)
myarray[i] = i * i * 2;
void Classy::printarray()
for(int i = 0; i < arraysize; i++)
std::cout << myarray[i] << std::endl;
编译器确实不喜欢我的方法,所以我正在寻找另一种处理方式。
我对这个主题进行了一些谷歌搜索,但我的搜索没有取得成果。我发现this 方法使用动态内存分配来实现。这是我想避免的事情,所以我正在寻找一个不依赖于此的解决方案。很可能(而且我开始认为)它是解决我的问题的唯一优雅解决方案(如果是这种情况,问题当然应该作为重复关闭)。
【问题讨论】:
使用std::vector
。
一般来说,对于大多数用途,我不是阵列的忠实拥护者。除非您真的需要它们进行一些感知优化,否则std::vector
是您的朋友,并且更有可能随着您的需求变化而变化。但是您可以使用 std::array ... 方便的 C++ 替代 C 数组。
@HostileFork:std::array
不是可变大小。 std::unique_ptr<T[]>
是在构造时设置大小的数组的标准组件。 std::vector<T>
用于在其生命周期内大小可以变化的数组。
更一般地说:您想了解new
(啊,当然还有delete
)的动态分配。
@BenVoigt 是的,我很清楚。但我最近讨论了这个问题,some people rabidly insist they want an array。去搞清楚。不要向信使开枪。
【参考方案1】:
需要使用动态分配,因为sizeof (Classy)
必须是编译时常量。对象的内部大小无法增长。但动态分配不必像该链接所暗示的那样复杂。
你可以这样做:
#include <memory>
class Classy
private:
int arraysize;
std::unique_ptr<int[]> myarray;
public:
Classy(int parraysize);
void printarray();
;
Classy::Classy(int parraysize)
: arraysizeparraysize
, myarraynew int[arraysize]
for(int i = 0; i < arraysize; i++)
myarray[i] = i * i * 2;
#include <iostream>
void Classy::printarray()
for(int i = 0; i < arraysize; i++)
std::cout << myarray[i] << std::endl;
这将允许大小在创建时发生变化,并在之后固定。 std::unique_ptr
会在你的对象死亡时自动销毁数组内容。
【讨论】:
【参考方案2】:你想用模板来解决这个问题:
#include <array>
template<std::size_t ArraySize>
class Classy final
public:
static const std::size_t size = ArraySize;
/* The rest of your public interface here */
private:
std::array<int, ArraySize> m_array;
;
然后你可以像这样使用你的类:
int main()
Classy<5> hasArrayOfFiveElements;
return 0;
您可以选择不使用 std::array,而不是使用 c 样式的数组。但是我们正在编写 C++,所以让我们使用我们可用的更好的语言工具:)
【讨论】:
这不会让您按照问题的要求“将大小传递给构造函数”。【参考方案3】:好吧,我认为在使用经典数组时不使用动态内存分配是无法做到的,但你可以使用 std::vector。你可以这样做:
#include <iostream>
class Classy
private:
int arraysize;
std::vector<int> myArrayOfInts;
public:
Classy(int parraysize);
void printarray();
;
Classy::Classy(int parraysize)
arraysize = parraysize;
for(int i = 0; i < arraysize; i++)
myArrayOfInts.push_back(i * i * 2);
void Classy::printarray()
for(int i = 0; i < myArrayOfInts.size(); i++) //you could also use arraysize, but then you
std::cout << myArrayOfInts[i] << std::endl;//must update it when you add or remove any
// element from vector
【讨论】:
std::vector
需要一个类型
是的,当然,我忘记写了 :D 谢谢,我已经更新了。
为什么用int arraysize;
跟踪std::vector
的大小?不能只用vector的size()
方法吗?
你可以。我试图尽可能少地编辑操作的代码。但最好用 size 方法。【参考方案4】:
您需要使用new[]
动态分配您的数组,然后在您的析构函数中使用delete[]
。或者,使用std::vector<int>
和reserve
传递给构造函数的数量。还有一种方法是使您的类模板化,将size_t
参数用于您希望它拥有的元素数量,但这完全消除了它的动态方面(您还不如使用std::array
点。
我知道您希望避免动态分配,但这是做您想做的最有效的方式(因为vector
可能占用比您预期更多的空间)。
【讨论】:
以上是关于如何在 C++ 类中初始化可变大小数组?的主要内容,如果未能解决你的问题,请参考以下文章