迭代器问题 [英] Problem with iterators

查看:80
本文介绍了迭代器问题的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

1)


我有这个代码:


std :: list< intmylist;

mylist .push_back(1);

mylist.push_back(2);

mylist.push_back(3);

mylist.push_back(4) ;


std :: list< int> :: iterator it_p = mylist.begin();

std :: list< int> :: iterator it_q = mylist.end();


std :: set< intmyset(it_p,it_q);


int first = * myset.begin ();

int second = * myset.end();

std :: cout<< first = <<第一个<< std :: endl;

std :: cout<< second = <<第二<< std :: endl;

我复制了list中的元素。到设置使用两个迭代器:

" it_p"和it_q。当我打印第一时和第二我得到1和4.但是

应该:


int second = * myset.end();


在*未定义的最后一个之后没有返回元素*的值?

我认为我必须将myset.end()递减1才能得到值4.
< br $> b $ b 2)


另一件事。据我所知,每个容器都支持特定的

迭代器。例如。 list只支持前向迭代器,而set支持

双向迭代器。


但是在哪里(已经尝试过)谷歌我找到了每个迭代器的列表/>
容器支持?

解决方案

desktop写道:


1 )


我有这个代码:


std :: list< intmylist;

mylist.push_back(1 );

mylist.push_back(2);

mylist.push_back(3);

mylist.push_back(4);


std :: list< int> :: iterator it_p = mylist.begin();

std :: list< int> :: iterator it_q = mylist.end ();


std :: set< intmyset(it_p,it_q);


int first = * myset.begin();

int second = * myset.end();



这会导致未定义的行为。由''end()''返回的迭代器是

不可解除引用。你可能想要''* myset.rbegin()''。


std :: cout<< first = <<第一个<< std :: endl;

std :: cout<< second = <<第二<< std :: endl;


我复制了list中的元素。到设置使用两个

迭代器:it_p和it_q。当我打印第一时和第二我得到了

1和4.但是应该:


int second = * myset.end();


在* *
undefined之后的*之后不返回元素*的值?我以为我不得不将myset.end()减1来

得到值4.



无论你认为你的程序应该如何做,这都错了。代码

有未定义的行为。


2)


另一件事。据我所知,每个容器都支持特定的

迭代器。例如。 list仅支持转发迭代器



错误。 std :: list支持双向迭代器。


虽然set支持

双向迭代器。


但是在哪里(尝试过)谷歌我找到了一个

容器支持的每个迭代器的列表?



获取标准副本。


V

-

请在通过电子邮件回复时删除资金''A'

我没有回复最热门的回复,请不要问


Victor Bazarov写道:


desktop写道:


> 1 )

我有这段代码:

std :: list< intmylist;
mylist.push_back(1);
mylist.push_back(2) ;
mylist.push_back(3);
mylist.push_back(4);

std :: list< int> :: iterator it_p = mylist.begin();
std :: list< int> :: iterator it_q = mylist.end();

std :: set< intmyset(it_p,it_q);

int first = * myset.begin();
int second = * myset.end();



这会导致未定义的行为。由''end()''返回的迭代器是

不可解除引用。你可能想要''* myset.rbegin()''。


> std :: cout<< first = <<第一个<< std :: endl;
std :: cout<< second = <<第二<< std :: endl;

我复制了list中的元素。到设置使用两个
迭代器:it_p和it_q。当我打印第一时和第二我得到了
1和4.但是应该:

int second = * myset.end();

在*之后不返回元素*的值最后哪个是未定义的?我认为我必须减少myset.end()一个来获得值4.



无论你认为你的程序应该做什么,它都是'一切都错了。代码

有未定义的行为。


> 2)

另一件事。据我所知,每个容器都支持特定的
迭代器。例如。 list只支持转发迭代器



错误。 std :: list支持双向迭代器。



在标准中它表示列表,向量和出队都是

序列。在页469它说迭代器应该至少是前进。

但是因为二进制减去'' - ''给出编译错误我认为他们不会支持
随机访问迭代器。是*至少*表示没有一点

不精确?


此外,i和j迭代器必须是输入迭代器类型。我不知道任何支持这种类型的容器或任何你可以使用的方式

制作输入迭代器。


是否对这些迭代器的使用进行限制,如果它们是在例如中使用的
。构造函数(你只允许使用运算符

作为输入迭代器,即使没有容器返回这种迭代器)?



桌面小包装:


1)


我有这个代码:

std :: list< intmylist;

mylist.push_back(1);

mylist.push_back(2);

mylist.push_back(3);

mylist.push_back(4);


std :: list< int> :: iterator it_p = mylist.begin( );

std :: list< int> :: iterator it_q = mylist.end();

std :: set< intmyset(it_p,it_q );


int first = * myset.begin();

int second = * myset.end();

std :: cout<< first = <<第一个<< std :: endl;

std :: cout<< second = <<第二<< std :: endl;


我复制了list中的元素。到设置使用两个迭代器:

" it_p"和it_q。当我打印第一时和第二我得到1和4.但是

应该:


int second = * myset.end();


在*未定义的最后一个*之后不返回元素*的值?

我认为我必须将myset.end()递减1以得到值4.



是的,你必须这样做。您发布的代码只调用未定义的

行为,

这意味着它可以导致实现者决定的任何内容,特别是
,它可以返回4,但在不同的平台上,它可能会导致

程序崩溃或返回-45246961或其他任何内容。


2)


另一件事。据我所知,每个容器都支持特定的

迭代器。例如。 list只支持前向迭代器,而set支持

双向迭代器。


但是在哪里(已经尝试过)谷歌我找到了每个迭代器的列表/>
容器支持?



每个容器都有一个特定的迭代器类。这个类满足

一些

概念(类似于界面),这些是输入/转发/

双向/ ...

[顺便说一句。这些之间存在层次结构]。可以在SGI STL手册中阅读每个容器的
迭代器要满足的
。例如,有了清单,




清单是可逆容器的型号


和a关于可逆容器的页面,有
....迭代器必须是双向迭代器


所以我们知道列表必须有一个迭代器至少和

双向一样强。


问候

Jiri Palecek


1)

I have this code:

std::list<intmylist;
mylist.push_back(1);
mylist.push_back(2);
mylist.push_back(3);
mylist.push_back(4);

std::list<int>::iterator it_p = mylist.begin();
std::list<int>::iterator it_q = mylist.end();

std::set<intmyset(it_p,it_q);

int first = *myset.begin();
int second = *myset.end();
std::cout << "first = " << first << std::endl;
std::cout << "second = " << second << std::endl;
I copy the elements from the "list" to the "set" with the two iterators:
"it_p" and "it_q". When I print "first" and "second" I get 1 and 4. But
should:

int second = *myset.end();

not return the value of the element *after* the last which is undefined?
I thought that I had to decrement myset.end() by one to get the value 4.

2)

Another thing. As I understand each container supports a specific
iterator. Eg. list only supports forward iterators while set supports
bidirectional iterators.

But where (have tried) google do I find a list of each iterator that a
container supports?

解决方案

desktop wrote:

1)

I have this code:

std::list<intmylist;
mylist.push_back(1);
mylist.push_back(2);
mylist.push_back(3);
mylist.push_back(4);

std::list<int>::iterator it_p = mylist.begin();
std::list<int>::iterator it_q = mylist.end();

std::set<intmyset(it_p,it_q);

int first = *myset.begin();
int second = *myset.end();

This causes undefined behaviour. The iterator returned by ''end()'' is
non-dereferenceable. You probably want ''*myset.rbegin()''.

std::cout << "first = " << first << std::endl;
std::cout << "second = " << second << std::endl;
I copy the elements from the "list" to the "set" with the two
iterators: "it_p" and "it_q". When I print "first" and "second" I get
1 and 4. But should:

int second = *myset.end();

not return the value of the element *after* the last which is
undefined? I thought that I had to decrement myset.end() by one to
get the value 4.

Whatever you think your program should do, it''s all wrong. The code
has undefined behaviour.

2)

Another thing. As I understand each container supports a specific
iterator. Eg. list only supports forward iterators

Wrong. std::list supports bidirectional iterators.

while set supports
bidirectional iterators.

But where (have tried) google do I find a list of each iterator that a
container supports?

Get a copy of the Standard.

V
--
Please remove capital ''A''s when replying by e-mail
I do not respond to top-posted replies, please don''t ask


Victor Bazarov wrote:

desktop wrote:

>1)

I have this code:

std::list<intmylist;
mylist.push_back(1);
mylist.push_back(2);
mylist.push_back(3);
mylist.push_back(4);

std::list<int>::iterator it_p = mylist.begin();
std::list<int>::iterator it_q = mylist.end();

std::set<intmyset(it_p,it_q);

int first = *myset.begin();
int second = *myset.end();


This causes undefined behaviour. The iterator returned by ''end()'' is
non-dereferenceable. You probably want ''*myset.rbegin()''.

>std::cout << "first = " << first << std::endl;
std::cout << "second = " << second << std::endl;
I copy the elements from the "list" to the "set" with the two
iterators: "it_p" and "it_q". When I print "first" and "second" I get
1 and 4. But should:

int second = *myset.end();

not return the value of the element *after* the last which is
undefined? I thought that I had to decrement myset.end() by one to
get the value 4.


Whatever you think your program should do, it''s all wrong. The code
has undefined behaviour.

>2)

Another thing. As I understand each container supports a specific
iterator. Eg. list only supports forward iterators


Wrong. std::list supports bidirectional iterators.

Ok in the standard it says that list, vector and dequeue all are
Sequences. On page 469 it says that iterator should at least be forward.
But since binary minus ''-'' gives a compile error I assume they don''t
support random access iterator. Is the *at least* formulation not a bit
un-precise?

Further the i and j iterators has to be of type input iterator. I don''t
know of any containers that supports this type or any way that you can
make an input iterator.

Is it to make restrictions on the use of these iterators if they are
used in the eg. constructor (you are only allowed to use the operators
for input iterators even though no containers return this kind of iterator)?



desktop napsal:

1)

I have this code:

std::list<intmylist;
mylist.push_back(1);
mylist.push_back(2);
mylist.push_back(3);
mylist.push_back(4);

std::list<int>::iterator it_p = mylist.begin();
std::list<int>::iterator it_q = mylist.end();

std::set<intmyset(it_p,it_q);

int first = *myset.begin();
int second = *myset.end();
std::cout << "first = " << first << std::endl;
std::cout << "second = " << second << std::endl;
I copy the elements from the "list" to the "set" with the two iterators:
"it_p" and "it_q". When I print "first" and "second" I get 1 and 4. But
should:

int second = *myset.end();

not return the value of the element *after* the last which is undefined?
I thought that I had to decrement myset.end() by one to get the value 4.

Yes, you have to do it. The code you''ve posted just invokes undefined
behaviour,
which means that it can result to anything the implementor decides,
particularly, it can return 4, but on a different platform, it might
crash the
program or return -45246961 or whatever else.

2)

Another thing. As I understand each container supports a specific
iterator. Eg. list only supports forward iterators while set supports
bidirectional iterators.

But where (have tried) google do I find a list of each iterator that a
container supports?

Each container has a specific iterator class. This class satisfies
some
concept (similar to interface), theses are the Input/Forward/
Bidirectional/...
[btw. there is a hierarchy between these]. What each container''s
iterator has
to satisfy, can be read in the SGI STL manual. For example, with list,
there is

list is a model of reversible container

and on a page about reversible container, there is

.... the iterators must be Bidirectional Iterators

so we know a list must hav an iterator at least as strong as
Bidirectional.

Regards
Jiri Palecek


这篇关于迭代器问题的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

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