支持“对于每个”在自定义const本地C ++容器类 [英] Supporting "for each" on custom const native C++ container class

查看:212
本文介绍了支持“对于每个”在自定义const本地C ++容器类的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想实现一个简单的本地C ++固定容量数组模板类,为了方便起见,支持基于范围的for each语法,并且开销最小。



<

使用此实现:

  template<类T,size_t Capacity> 
class List
{
public:
List(){mSize = 0; }

const T * begin()const {return mItems; }
const T * end()const {return mItems + mSize; }

T * begin(){return mItems; }
T * end(){return mItems + mSize; }

private:
size_t mSize;
T mItems [Capacity];
};

和此用法:

  const List< int,5> myInts; 
(const int myInt in myInts)
{
continue;
}

我收到此错误:


$ b b

 错误C2440:'initializing':无法从'const int *'转换为'int *'
转换失去限定符

此用法不会引起抱怨:

 列表< int,5> myInts; 
(const int myInt in myInts)
{
continue;
}

这个(不需要的)实现不会抱怨:

  template<类T,size_t Capacity> 
class List
{
public:
List(){mSize = 0; }

T * begin()const {return const_cast< List *>(this) - > mItems; }
T * end()const {return const_cast< List *>(this) - > mItems + mSize; }

private:
size_t mSize;
T mItems [Capacity];
};

发生什么事情,我不明白?它是什么关于std :: vector<>处理这个正确?谢谢!

解决方案

你的使用情况似乎有点奇怪,因为你没有C ++中的每个结构,它下来。在C ++ 11中引入了用于和基于范围的用于。我只能猜测你的真实用例是什么,但最可能的编译器抱怨由于const正确性错误。我不能真正地确定你的错误,没有一个真正的代码,你试图运行。无论如何,下面是一个演示两种用法的工作示例。希望这是有帮助的,但如果你有任何问题 - 随时跟进,我会尝试解释。

  #include < cstdlib> 
#include< iostream>

template< typename T,std :: size_t Capacity>
class List {
public:
List():mSize(0){}

const T * begin()const {return mItems; }
const T * end()const {return mItems + mSize; }

T * begin(){return mItems; }
T * end(){return mItems + mSize; }

void add(int v)
{
// TODO:在这里检查是否超出范围...
mItems [mSize ++] = v;
}

private:
size_t mSize;
T mItems [Capacity];
};

int main()
{
/ * const * / List< int,10>数组;

array.add(1);
array.add(11);
array.add(15);
array.add(3);

// C ++ 11风格(基于范围)
for(int p:array){
std :: cout< p < '\\\
';
}

// Pre C ++ 11 style
for(const int * from = array.begin(),* to = array.end(); from!= to; ++ from)
{
int p = * from;
std :: cout<< p < '\\\
';
}
}


I'd like to implement a simple native C++ fixed-capacity array template class, supporting the range-based "for each" syntax for convenience, with minimal overhead.

I'm having trouble with supporting it on const instances.

With this implementation:

template< class T, size_t Capacity >
class List
{
public:
    List() { mSize = 0; }

    const T* begin() const { return mItems; }
    const T* end() const { return mItems + mSize; }

    T* begin() { return mItems; }
    T* end() { return mItems + mSize; }

private:
    size_t mSize;
    T mItems[ Capacity ];
};

and this usage:

const List< int, 5 > myInts;
for each( const int myInt in myInts )
{
    continue;
}

I get this error:

error C2440: 'initializing' : cannot convert from 'const int *' to 'int *'
    Conversion loses qualifiers

This usage doesn't complain:

List< int, 5 > myInts;
for each( const int myInt in myInts )
{
    continue;
}

And this (undesirable) implementation doesn't complain:

template< class T, size_t Capacity >
class List
{
public:
    List() { mSize = 0; }

    T* begin() const { return const_cast< List* >( this )->mItems; }
    T* end() const { return const_cast< List* >( this )->mItems + mSize; }

private:
    size_t mSize;
    T mItems[ Capacity ];
};

What is going on under the hood that I'm not understanding? What is it about std::vector<> that handles this properly? Thanks!

解决方案

Your use-case seems a bit strange for me as there is no for each constructs in C++ as you have written it down. There is a regular for and range-based for introduced in C++11. I can only guess what your real use case is, but most likely compiler complains due to const-correctness mistake. I cannot really pin down your mistake exactly without a real code that you are trying to run. At any rate, below is a working example demonstrating both usages. Hope it is helpful, but if you have any questions — feel free to follow up, I will try to explain.

#include <cstdlib>
#include <iostream>

template <typename T, std::size_t Capacity>
class List {
  public:
    List() : mSize(0) {}

    const T *begin() const { return mItems; }
    const T *end() const { return mItems + mSize; }

    T *begin() { return mItems; }
    T *end() { return mItems + mSize; }

    void add(int v)
    {
        // TODO: Check for out of range here...
        mItems[mSize++] = v;
    }

  private:
    size_t mSize;
    T      mItems[Capacity];
};

int main()
{
    /* const */ List<int, 10> array;

    array.add(1);
    array.add(11);
    array.add(15);
    array.add(3);

    // C++11 style (range-based for)
    for (int p : array) {
        std::cout << p << '\n';
    }

    // Pre C++11 style
    for (const int *from = array.begin(), *to = array.end(); from != to; ++from)
    {
        int p = *from;
        std::cout << p << '\n';
    }
}

这篇关于支持“对于每个”在自定义const本地C ++容器类的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆