2013-06-26 3 views
0

При попытке выяснить проблему, которая возникает только в сборке релиза, а не в сборке отладки, я заметил следующее поведение (String было бы недействительным и не указывало бы на что-либо, в то время как int будь умницей). Я дал ниже код, который дает представление о том, что я собирался черезПоведение в выпуске сборки Я не могу понять

typedef boost::shared_ptr<MyClass> shared_cls 
typedef std::deque<shared_cls> vector_def; 
typedef boost::shared_ptr<vector_def> shared_vector_def; 
typedef boost::unordered_map<int,shared_vector_def> inner_map_def; 
typedef boost::shared_ptr<inner_map_def> shared_inner_map_def; 
static boost::unordered_map<std::string,shared_inner_map_def> bcontainer; 

shared_cls& SomeMethod(const std::string& symb,const int& no) 
{ 
    shared_inner_map_def tshare = bcontainer[symb]; 
    shared_vector_def tmp = tshare->at(no); 
    shared_cls t = tmp->back(); 
    return t 
} 

объект MyClass выглядит как этот

 class SomeClass 
     { 
      private: 
      int i; 
      std::string s; 
      void set_i(int rx) 
      { 
      i = rx; 
      } 
      int get_i() 
      { 
       return i; 
      } 
      void set_s(std::string rx) 
      { 
      s = rx; 
      } 
      std::string get_s() 
      { 
       return s; 
      } 
     } 

Теперь, когда я использую выше метод, как показано в следующем коде

void main() 
{ 
    shared_cls r = SomeMethod("IBM",12); 
    //Here r does not have a valid string s 
    //However it does have a valid int i 
} 

Теперь мой вопрос находится в приведенном выше main, когда я вызываю SomeMethod. Возвращаемое значение r не имеет допустимой строки s. У меня есть скремблированное значение, которое я нашел это, используя регистратор. Однако значение s полностью находится во время функции SomeMethod. Я решил эту проблему, не возвращая общий указатель по ссылке. В этом случае он работает. Почему удаление ссылки заставляет его работать

+2

Вы должны получить большое смелое предупреждение от любого достойного компилятора при попытке вернуть ссылку на временный объект! –

+0

Не указывает этот указатель на объект, который присутствует в статическом контейнере. – MistyD

+0

@MistyD, кажется, что ваш опубликованный код не является полным –

ответ

0

Ваш shared_cls t выходит за пределы сферы действия, поскольку он определен в функции SomeMethod. Вам нужно вернуть общие указатели по значению, если они определены в области. В link объясняется, почему опасно возвращать ссылку временного объекта.

В случае std :: string, строка имеет механизм подсчета ссылок, а когда эта ссылка уменьшена до нуля, она становится недействительной и в этом случае может наблюдаться ошибка сегментации. Даже если элемент int i возвращается правильно, это по-прежнему неопределенное поведение.

+0

Итак, почему значение int должно быть там, и только строка повреждена? – MistyD

+1

Из-за неопределенного поведения. –

Смежные вопросы