Переменная, установленная внутри цикла BOOST_FOREACH, недопустима вне цикла, почему? - PullRequest
1 голос
/ 26 ноября 2010

BOOST_FOREACH делает недействительным слабый_птр, который находится в качестве члена в классе GroupMember, пожалуйста, помогите мне понять, почему.

Код ниже объясняет ошибку:

class GroupMember
{
  bool logInState;
  boost::weak_ptr<CUser> wpUser;
};

GroupMember::iterator it;

BOOST_FOREACH(EachLevel aLevel, levels)
{
  if(aLevel.exist(spUser))
  {
    it = aLevel.getIteratorToGroupMember( spUser );
    //iterator (it) is valid as well as the group member's attributes (and weak_ptr)
  }
}

//Iterator (it) seems to be valid but the weak_ptr is invalid. 
//The counter to the object is more than 10 so the weak ptr is not expired.

Код ниже работает отлично:

GroupMember::iterator it;
std::vector<EachLevel>::iterator itLevel;
for(itLevel = levels.begin(); itLevel != levels.end(); ++itLevel)
{
  if(itLevel->exist(spUser))
      it = itLevel->getIteratorToGroupMember( spUser );
}

//Here is iterator (it) valid (including the weak_ptr)

Я не вижу разницы, не так ли?

Спасибо!

Ответы [ 2 ]

3 голосов
/ 26 ноября 2010

Вы предположили, что BOOST_FOREACH реализован как во втором фрагменте кода, что является неверным предположением.

Во-вторых, в вашем BOOST_FOREACH вы выполняете итерацию по значению. Попробуйте по ссылке:

BOOST_FOREACH(EachLevel& aLevel, levels) 

и посмотрите, работает ли он.

3 голосов
/ 26 ноября 2010

EachLevel aLevel создает локальный объект aLevel, область действия которого находится только в пределах BOOST_FOREACH. Если вы возьмете iterator от этого объекта, он будет недопустимым вне цикла. Вы можете изменить его на ссылку, объявив EachLevel& aLevel, чтобы копия не создавалась и ваш итератор оставался действительным. Во втором случае вы напрямую обращаетесь к объекту, не создавая его копию, следовательно, он работает.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...