C++ 实现具有迭代器支持的通用固定大小数组
我需要一个数组,其中大小在编译时是已知的。我知道我可以使用std::vector或boost::array。但这并没有教会我如何在内部工作。此外,除了使用初始值设定项外,我找不到如何将项添加到boost::array中。我已经为泛型数组编写了以下代码。我的目的是熟悉迭代器、模板专门化等C++ 实现具有迭代器支持的通用固定大小数组,c++,arrays,templates,iterator,C++,Arrays,Templates,Iterator,我需要一个数组,其中大小在编译时是已知的。我知道我可以使用std::vector或boost::array。但这并没有教会我如何在内部工作。此外,除了使用初始值设定项外,我找不到如何将项添加到boost::array中。我已经为泛型数组编写了以下代码。我的目的是熟悉迭代器、模板专门化等 template<typename T> struct iterator_traits { typedef T value_type; typedef T&
template<typename T>
struct iterator_traits
{
typedef T value_type;
typedef T& reference_type;
typedef T* iterator;
typedef const T* const_iterator;
typedef std::reverse_iterator<iterator> reverse_iterator;
};
template<typename T>
struct iterator_traits<T*>
{
typedef T* value_type;
typedef T*& reference_type;
typedef T** iterator;
typedef const T const_iterator;
typedef std::reverse_iterator<iterator> reverse_iterator;
};
template<typename T, size_t size = 10>
class Array
{
public:
typedef typename iterator_traits<T>::value_type value_type;
typedef typename iterator_traits<T>::reference_type reference_type;
typedef typename iterator_traits<T>::iterator iterator;
typedef typename iterator_traits<T>::const_iterator const_iterator;
typedef typename iterator_traits<T>::reverse_iterator reverse_iterator;
Array() : lastIndex(0) {
}
void add(value_type element) {
if(lastIndex >= size)
throw std::out_of_range("Array is full");
array_[lastIndex++] = element;
}
reference_type at(unsigned int index){
if(index < size)
return array_[index];
else
throw std::out_of_range("Invalid index");
}
size_t capacity(){
return size;
}
iterator begin(){
return array_;
}
iterator end(){
return array_ + size;
}
const_iterator begin() const{
return array_;
}
const_iterator end() const{
return array_ + size;
}
reverse_iterator rbegin() {
return reverse_iterator(end());
}
reverse_iterator rend() {
return reverse_iterator(begin());
}
private:
value_type array_[size];
unsigned int lastIndex;
};
模板
结构迭代器
{
类型定义T值_类型;
类型定义T和参考类型;
typedef T*迭代器;
typedef常量T*常量迭代器;
typedef std::reverse_迭代器reverse_迭代器;
};
模板
结构迭代器
{
类型定义T*值_类型;
类型定义T*&参考类型;
类型定义T**迭代器;
typedef常量T常量迭代器;
typedef std::reverse_迭代器reverse_迭代器;
};
模板
类数组
{
公众:
typedef typename迭代器_traits::value_type value_type;
typedef typename迭代器_traits::reference_type reference_type;
typedef typename迭代器_traits::迭代器迭代器;
typedef typename迭代器_traits::const_迭代器const_迭代器;
typedef typename迭代器特征::反向迭代器反向迭代器;
数组():lastIndex(0){
}
无效添加(值类型元素){
如果(lastIndex>=大小)
抛出标准::超出范围(“数组已满”);
数组\[lastIndex++]=元素;
}
引用类型at(无符号整数索引){
如果(索引<大小)
返回数组\[index];
其他的
抛出标准::超出范围(“无效索引”);
}
尺寸/容量(){
返回大小;
}
迭代器begin(){
返回数组;
}
迭代器结束(){
返回数组+大小;
}
常量迭代器begin()常量{
返回数组;
}
常量迭代器end()常量{
返回数组+大小;
}
反向迭代器rbegin(){
返回反向迭代器(end());
}
反向迭代器rend(){
返回反向迭代器(begin());
}
私人:
值_类型数组_u[size];
无符号整数索引;
};
上述代码运行良好。以下是我的问题
1-如何像boost::array那样创建阵列?差不多
Array<int> ints = { 10, 12 };
// type definitions
typedef T value_type;
typedef T* iterator;
typedef const T* const_iterator;
typedef T& reference;
typedef const T& const_reference;
typedef std::size_t size_type;
typedef std::ptrdiff_t difference_type;
Array<int> ints = { 10, 12 };
Array int={10,12};
2-代码中是否存在任何陷阱
3-我必须对traits中的指针类型使用专门化。这是最好的做法吗
4-迭代器模式是否正确实现
任何想法都很好 boost::array使用了该语言的一个特性:没有构造函数的结构可以使用初始化列表。如果提供自己的构造函数,则不能使用初始化列表 另外,您使用的迭代器是错误的。您的代码应该类似于
Array<int> ints = { 10, 12 };
// type definitions
typedef T value_type;
typedef T* iterator;
typedef const T* const_iterator;
typedef T& reference;
typedef const T& const_reference;
typedef std::size_t size_type;
typedef std::ptrdiff_t difference_type;
Array<int> ints = { 10, 12 };
迭代器特征是迭代器的特征。此外,您还可以将指针用作迭代器。STL明确地允许这一点。boost::array使用了该语言的一个特性:没有构造函数的结构可以使用初始化列表。如果提供自己的构造函数,则不能使用初始化列表 另外,您使用的迭代器是错误的。您的代码应该类似于
Array<int> ints = { 10, 12 };
// type definitions
typedef T value_type;
typedef T* iterator;
typedef const T* const_iterator;
typedef T& reference;
typedef const T& const_reference;
typedef std::size_t size_type;
typedef std::ptrdiff_t difference_type;
Array<int> ints = { 10, 12 };
迭代器特征是迭代器的特征。此外,您还可以将指针用作迭代器。STL明确允许这一点。2-是否存在任何陷阱 我会去掉默认的大小“size=10”。什么使10成为数组的默认大小?相反,我看到的情况是,有人不小心遗漏了尺寸,并假设它比实际尺寸大
关于添加元素和C风格的初始化,我不认为两者都可以。它在boost中起作用,因为(我相信)这个对象很简单,就是一个隐藏的数组。它不能动态地重新调整大小。该类只是将迭代器(以及其他类似sugar的::at())添加到普通数组中。2-是否存在任何陷阱 我会去掉默认的大小“size=10”。什么使10成为数组的默认大小?相反,我看到的情况是,有人不小心遗漏了尺寸,并假设它比实际尺寸大
关于添加元素和C风格的初始化,我不认为两者都可以。它在boost中起作用,因为(我相信)这个对象很简单,就是一个隐藏的数组。它不能动态地重新调整大小。该类只是将迭代器(以及其他类似sugar的::at())添加到普通数组中。1-如何创建类似boost::array的数组?差不多
Array<int> ints = { 10, 12 };
// type definitions
typedef T value_type;
typedef T* iterator;
typedef const T* const_iterator;
typedef T& reference;
typedef const T& const_reference;
typedef std::size_t size_type;
typedef std::ptrdiff_t difference_type;
Array<int> ints = { 10, 12 };
Array int={10,12};
在C++中,如果结构、联合或C样式数组符合聚合标准,则只能(当前)使用括号封闭的初始化列表。为此,根据标准:
8.5.1.1聚合是一个数组或类(第9条),没有用户提供的构造函数(12.1),没有私有或受保护的非静态数据成员(第11条),没有基类(第10条),也没有虚拟函数(10.3)
如果您想在当前标准中使用这些特性,就必须使您的类具有这些特性。下一个标准(请参阅)包括允许其他类型这样做的规定
2-代码中是否存在任何陷阱
这里有一个原因:您不能将内容添加到boost列表中的原因是它总是具有相同数量的元素(分配给它的大小)。在数组中,您可以添加元素,但在构建过程中,您仍然在引擎盖下方构建了10个元素。如果用户不希望默认构造函数调用10次,那么这可能会导致一些令人惊讶的结果。1-如何像boost::array那样创建我的数组?差不多
Array<int> ints = { 10, 12 };
// type definitions
typedef T value_type;
typedef T* iterator;
typedef const T* const_iterator;
typedef T& reference;
typedef const T& const_reference;
typedef std::size_t size_type;
typedef std::ptrdiff_t difference_type;
Array<int> ints = { 10, 12 };