C++ 可以用作固定大小(堆栈)和动态大小(堆)的数组封装器
昨天,我偶然发现了一个名为Eigen的库,它提供了如下签名:-C++ 可以用作固定大小(堆栈)和动态大小(堆)的数组封装器,c++,arrays,c++11,stack,heap-memory,C++,Arrays,C++11,Stack,Heap Memory,昨天,我偶然发现了一个名为Eigen的库,它提供了如下签名:- Array<float,Dynamic,1> b;//<--- dynamic = unknown at compile time Array<float,3,1> c;//<--- both row(=3) and col(=1) known at compile time 我认为它非常酷,因为它可以避免不必要的堆分配。 它在某些情况下非常合适 问题: 1个类< >中支持C++
Array<float,Dynamic,1> b;//<--- dynamic = unknown at compile time
Array<float,3,1> c;//<--- both row(=3) and col(=1) known at compile time
我认为它非常酷,因为它可以避免不必要的堆分配。它在某些情况下非常合适 问题: <> 1个类< <强> >中支持C++的技术/语义是什么?p> 背后有什么想法?
我不是要完整的代码或任何片段,但我不介意 答案可以忽略关于如何实现特征阵列的所有事实。(艾根只是一个例子。) 我想要一些可靠的想法来改进我自己的阵列封装器,让它变得如此酷 我拙劣的解决方案
- 为两个场景(动态和修复)创建字段,但在每个场景中,仅使用其中的一些字段李>
- 然后,spam
控制动态vs常量,但我认为这是反模式的std::enable_if
数组
类模板将存储的创建委托给另一个类模板,该类模板部分专用于它们命名为动态
的某个神奇值
以下是一个基本示例:
#include <memory>
constexpr int Dynamic = -1;
template <typename T, int N>
struct Storage
{
Storage() : data{} {}
T data[N];
};
template <typename T>
struct Storage<T, Dynamic>
{
Storage(int count) : data{new T[count]} {}
Storage() = delete;
std::unique_ptr<T[]> data;
};
template <typename T, int N>
struct Array
{
Array() : storage{} {}
Array(int count) : storage{count} {}
Storage<T, N> storage;
};
int main() {
Array<int, 4> a1;
//Array<int, 4> a2(10); // Error since base Storage template has no constructor taking int.
Array<int, Dynamic> a3(10);
//Array<int, Dynamic> a4{}; // Error since Storage<T, Dynamic> has its default constructor deleted.
}
#包括
constexpr int Dynamic=-1;
模板
结构存储
{
存储():数据{}{}
T数据[N];
};
模板
结构存储
{
存储(整数计数):数据{new T[count]}{}
存储()=删除;
std::唯一的ptr数据;
};
模板
结构数组
{
数组():存储{}{}
数组(整数计数):存储{count}{}
储存;
};
int main(){
阵列a1;
//数组a2(10);//错误,因为基本存储模板没有接受int的构造函数。
阵列a3(10);
//数组a4{};//错误,因为存储已删除其默认构造函数。
}
基本上有两个不同的存储
模板,一个将在N==动态
时使用,另一个将用于任何其他值
事实上,如果你看一下,你会看到一个与我的例子相似的模式。有更多的专门化来支持多个维度和各种不同对齐的数据类型,但这是同一个概念。它们通过部分专门化来实现。基本上,
数组
类模板将存储的创建委托给另一个类模板,该类模板部分专用于它们命名为动态
的某个神奇值
以下是一个基本示例:
#include <memory>
constexpr int Dynamic = -1;
template <typename T, int N>
struct Storage
{
Storage() : data{} {}
T data[N];
};
template <typename T>
struct Storage<T, Dynamic>
{
Storage(int count) : data{new T[count]} {}
Storage() = delete;
std::unique_ptr<T[]> data;
};
template <typename T, int N>
struct Array
{
Array() : storage{} {}
Array(int count) : storage{count} {}
Storage<T, N> storage;
};
int main() {
Array<int, 4> a1;
//Array<int, 4> a2(10); // Error since base Storage template has no constructor taking int.
Array<int, Dynamic> a3(10);
//Array<int, Dynamic> a4{}; // Error since Storage<T, Dynamic> has its default constructor deleted.
}
#包括
constexpr int Dynamic=-1;
模板
结构存储
{
存储():数据{}{}
T数据[N];
};
模板
结构存储
{
存储(整数计数):数据{new T[count]}{}
存储()=删除;
std::唯一的ptr数据;
};
模板
结构数组
{
数组():存储{}{}
数组(整数计数):存储{count}{}
储存;
};
int main(){
阵列a1;
//数组a2(10);//错误,因为基本存储模板没有接受int的构造函数。
阵列a3(10);
//数组a4{};//错误,因为存储已删除其默认构造函数。
}
基本上有两个不同的存储
模板,一个将在N==动态
时使用,另一个将用于任何其他值
事实上,如果你看一下,你会看到一个与我的例子相似的模式。有更多的专门化来支持多个维度和各种不同对齐的数据类型,但这是同一个概念。这是一个模板类,因此您可以使用enable\u if with is\u算法来进行模板专门化。这里有一个例子:@Jerry Jeremiah这是一个非常好的链接,谢谢。这实际上可能是一个答案。它是一个模板类,所以您可以使用enable\u if with is\u算法来进行模板专门化。这里有一个例子:@Jerry Jeremiah这是一个非常好的链接,谢谢。这实际上可能是一个答案。