将索引转换为迭代器

时间:2014-09-12 15:26:39

标签: c++ indexing iterator openframeworks

我想用迭代器重新创建以下代码,仅用于学习目的。下面的代码检查openFrameworks中框的边界,基本上它检查当我的鼠标位置在4个矩形中的一个上时,它会将布尔值变为true而其他的变为false。我最近一直非常喜欢迭代器,但由于某些原因我无法使用迭代器,因为索引返回向量中对象的位置,迭代器返回指向该位置对象的指针。这是代码:

 for ( int i = 0; i < answersBox.size(); i++){
    for ( int j = 0; j < isHovered.size(); j++){
        if( x > answersBox[i].x && x < (answersBox[i].x + answersBox[i].width) && y > answersBox[i].y && y < (answersBox[i].y + answersBox[i].height)){
         if( i == j){
                isHovered[j] = true;
                cout << "This boolean number: " << j << " has become: " << isHovered[j] << endl;
            }else if( i != j){
                isHovered[j] = false;
            }
            }{
                cout << " These booleans number: " << j << " have become: " << isHovered[j] << endl;
        }
    }
}

谢谢!

3 个答案:

答案 0 :(得分:3)

你不应该盲目地将所有基于索引的循环转换为基于迭代器的循环。正如您所发现的,基于索引的循环有时可能更好(如:更容易阅读,编写,理解和维护)。

特别是以下代码:

if( i == j)

是一个很好的指标,基于索引的循环对于此特定问题更好

如果真的想要使用迭代器进行尝试,请查看std::distance。使用该函数,您可以将索引比较替换为:

if (std::distance(answersBox.begin(), iter1) == std::distance(isHovered.begin(), iter2)

顺便说一下,else if( i != j)没有意义,因为条件总是如此。您可以使用简单的else替换它。

答案 1 :(得分:0)

我认为你不能让这个代码在迭代器上工作,因为你无法比较两个迭代器,指向不同的容器。

如果要将迭代器作为索引进行比较,可以编写

if(i-answersBox.begin()==j-isHovered.begin() )

答案 2 :(得分:0)

这个怎么样?

typedef std::vector<std::pair<AnswerBox, bool> > answers_type;
answers_type answersBox;

for (answers_type::iterator i = answersBox.begin(); i != answersBox.end(); ++i)
{
  i->second = i->first->contains(x, y);
}

向量存储两者,AnswerBox以及是否悬停。

在这里,我使用了更加面向对象的定义方法

bool AnswerBox::contains(float x, float y) const
{
  return x > m_x && y > m_y && x < m_x + m_width && y < m_y + m_height;
}

其中m_ *是AnswerBox的成员变量(添加了前缀)。

PS更好的是为std :: pair使用自定义类。使事情更具可读性。即,std::vector<AnswerBoxHovered>元素包含AnswerBoxbool m_is_hovered。你得到的代码如下:

i->set_is_hovered(x, y);

,其中

void AnswerBoXHovered::set_is_hovered(float x, float y)
{
  m_is_hovered = m_answer_box.contains(x, y);
}