简体   繁体   English

具有移动end()的正向迭代器

[英]Forward iterator with a moving end()

So, I'm designing a class which connects (over network) to a service to receive some data. 因此,我正在设计一个类(通过网络)连接到服务以接收一些数据的类。 I don't know how man data points I will be receiving in advance. 我不知道我将如何预先接收人工数据点。 Nevertheless I was wondering, if there is a way to make this class iterable using a forward_iterator in order to enjoy the STL in its full glory. 但是,我想知道,是否有一种方法可以使用forward_iterator使该类可迭代,以便充分享受STL的乐趣。 My idea was something like: 我的想法是这样的:

self_type operator++() {
  // if there are some locally cached data points left return next
  // else connect to service again to receive the next batch of data
}

However, as I cannot provide a valid end() , I'm curious, if this is somehow still possible to do. 但是,由于我不能提供有效的end() ,我很好奇,如果仍然可以做到这一点。

An alternative (and iterator-less) interface would probably look something like: 一个替代的(且无迭代器的)接口可能类似于:

bool hasMoreDataPoints() const;
DataPoint& getNext();

which obviously won't work with any STL-algorithm. 这显然不适用于任何STL算法。

Do as the standard library do with istream_iterator : when you run out of data, set your iterator state such that it compares equal to a default-constructed object of that type. 像使用istream_iterator的标准库一样进行操作:当数据用尽时,请设置迭代器状态,使其与该类型的默认构造对象进行比较。 And then there's your end() equivalent. 然后是您的end()等效项。

I suppose there is some type of storage which you use in your class for caching, eg a std::vector . 我想您可以在类中使用某种类型的存储来进行缓存,例如std::vector You can then just expose its std::begin() and std::end() iterators (in all the usual forms). 然后,您可以仅公开其std::begin()std::end()迭代器(以所有常用形式)。 Algorithms then directly work on the underlying container, and use the container-iterator's member functions like operator++ , operator== and so on. 然后,算法直接在基础容器上工作,并使用容器迭代器的成员函数,例如operator++operator==等。

In case you need to introduce more logic, you need to create your custom iterator. 如果需要引入更多逻辑,则需要创建自定义迭代器。 Such can be basically done by composition, ie write a new class which contains an iterator corresponding to your storage container, and expose all functionality you need while adjusting it accordingly. 这基本上可以通过组合来完成,即编写一个包含与您的存储容器相对应的迭代器的新类,并公开您所需的所有功能,同时进行相应的调整。


EDIT: as you said you use a list: 编辑:正如您所说的,您使用列表:

struct DataPoints
{
    std::list<double> _list; 
    auto begin() const
    {
        return _list.begin();
    }
    auto end() const
    {
        return _list.end();
    }
    //other versions: non-const begin and end, cbegin, cend
}

That's it already for the simple approach. 简单的方法就已经足够了。 You can use that just as a normal list: 您可以将其用作普通列表:

DataPoints d;
std::find(d.begin(), d.end(), 10.0);

As said, if you need more logic, you probably need to write a custom iterator. 如前所述,如果您需要更多逻辑,则可能需要编写自定义迭代器。

However, as I cannot provide a valid end(), I'm curious, if this is somehow still possible .... 但是,由于我不能提供有效的end(),我很好奇,如果仍然可以做到这一点 ...。

You could use any of the container classes that comes with STL. 您可以使用STL随附的任何容器类。 Assume you are using a vector or a list or any other suitable container. 假设您正在使用向量或列表或任何其他合适的容器。 Just use what's provided by STL and write your own wrapper 只需使用STL提供的内容并编写自己的包装器

vector<datapoint> mydpvector;

//as data comes in
mydpvector.push_back(newdp);

vector<datapoint>::const_iterator cit=mydpvector.begin();
//now iterate everytime over the container

for(cit;cit!=mydpvector.end();cit++)
{
//get the data you need
}

//alternately if you need just the last element do this
mostrecentdp = mydpvector.back();

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM