难以理解运行时错误 this->is_initialized( ) failure in boost::optional
Difficult to understand runtime error this->is_initialized( ) failure in boost::optional
我有一两个文件似乎正在使用 boost::optional。但是抛出的错误非常不友好。我只是不知道从哪里开始寻找解决此错误的方法。它没有指向我拥有的一行代码。相反,它从 optional.hpp 开始,这是一个 boost 头文件,这是唯一抛出的消息。
/usr/include/boost/optional/optional.hpp:1191: boost::optional<T>::reference_type boost::optional<T>::get()
[with T = tev::events::EventItemCategory; boost::optional<T>::reference_type = tev::events::EventItemCategory&]: Assertion `this->is_initialized()' failed.
这是我从 gdb 得到的:
(gdb) c
Continuing.
/usr/include/boost/optional/optional.hpp:1191: boost::optional<T>::reference_type boost::optional<T>::get() [with T = tev::events::EventItemCategory; boost::optional<T>::reference_type = tev::events::EventItemCategory&]:
Assertion `this->is_initialized()' failed.
Program received signal SIGABRT, Aborted.
0x0000007f9c105064 in ?? ()
(gdb) bt
#0 0x0000007f9c105064 in ?? ()
#1 0x0000007f9c13c898 in ?? ()
Backtrace stopped: previous frame inner to this frame (corrupt stack?)
(gdb) q
valgrind 输出
==32083== Warning: invalid file descriptor -1 in syscall close()
==32083== at 0x4C8A574: close (in /lib/libpthread-2.25.so)
==32083== by 0x4A24123: setFilename(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (in /opt/ad/lib/libconfiguration.so)
==32083== by 0x4A25A4F: (std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&, std::__cxx11::basic_string<char, std::char
==32083== by 0x4A31FFB: Configuration() (in /opt/ad/lib/libconfiguration.so)
==32083== by 0x5484DF: GetInstance (Singleton.h:80)
==32083== by 0x5484DF: RecordingFactory::RecordingFactory() (RecordingFactory.cpp:18)
==32083== by 0x56D3C7: GetInstance (Singleton.h:39)
==32083== by 0x56D3C7: Service(bool&, std::shared_ptr<tev::events::EventServiceResource> const&, int) (Service.cpp:59)
==32083== by 0x4D391B: ABCService (ABC.h:38)
==32083== by 0x4D391B: void create_service_thread<trc::Service>(std::vector<unsigned long, std::allocator<unsigned long> >&, std::vector<ABCServiceBase*, std::allocator<ABCServiceBase*> >&, bool&,
==32083== by 0x4B3DF7: main (ABC.cpp:140)
/arm/release/usr/include/boost/optional/optional.hpp:1191: boost::optional<T>::reference_type boost::optional<T>::get()
[with T = tev::events::EventItemCategory; boost::optional<T>::reference_type = tev::events::EventItemCategory&]: Assertion `this->is_initialized()' failed.
==32083==
==32083== Process terminating with default action of signal 6 (SIGABRT)
==32083== at 0x63BA064: raise (in /lib/libc-2.25.so)
==32083==
==32083== HEAP SUMMARY:
==32083== in use at exit: 8,217,174 bytes in 9,658 blocks
==32083== total heap usage: 59,869 allocs, 50,211 frees, 13,722,597 bytes allocated
==32083==
==32083== Searching for pointers to 9,658 not-freed blocks
==32083== Checked 104,459,168 bytes
==32083==
==32083== 8 bytes in 1 blocks are still reachable in loss record 1 of 2,795
==32083==
MSVP
#include<iostream>
#include <boost/optional.hpp>
using namespace std;
class Myclass
{
public:
int a;
};
boost::optional<Myclass> func(int a)
{
boost::optional<Myclass> value;
if(a == 0)
{
/* This results in the same runtime error discussed in the question */
value->a = {200};
/* The following #if 0 , if enabled would remove the error */
#if 0
Myclass c;
c.a = 200;
value = c;
#endif
}
return value;
}
int main(int argc, char **argv)
{
boost::optional<Myclass> v = func(0);
if(v)
std::cout << v -> a << std::endl;
else
std::cout << "Uninitialized" << std::endl;
std::cin.get();
return 0;
}
->
运算符的使用仅在optional
初始化时有效。 Boost
决定触发断言失败并中止。
假设 optional
允许您像您尝试的那样修改单个字段。那么它就无法判断该对象是否已完全初始化并且应该被销毁。所以,API让你完全初始化optional
持有的对象,这样当optional
析构时,它知道是否需要销毁持有的对象。
如果您希望 optional
使用默认构造的实例进行初始化,那么您可以在代码中明确说明。
boost::optional<Myclass> value = Myclass();
value->a = 200;
对于您的用例,更直接的方法是简单地 return class 实例,然后初始化 optional
return 值,然后 return boost::none
表示 optional
未初始化。
Myclass c;
if(a == 0)
{
c.a = 200;
return c;
}
return boost::none;
我有一两个文件似乎正在使用 boost::optional。但是抛出的错误非常不友好。我只是不知道从哪里开始寻找解决此错误的方法。它没有指向我拥有的一行代码。相反,它从 optional.hpp 开始,这是一个 boost 头文件,这是唯一抛出的消息。
/usr/include/boost/optional/optional.hpp:1191: boost::optional<T>::reference_type boost::optional<T>::get()
[with T = tev::events::EventItemCategory; boost::optional<T>::reference_type = tev::events::EventItemCategory&]: Assertion `this->is_initialized()' failed.
这是我从 gdb 得到的:
(gdb) c
Continuing.
/usr/include/boost/optional/optional.hpp:1191: boost::optional<T>::reference_type boost::optional<T>::get() [with T = tev::events::EventItemCategory; boost::optional<T>::reference_type = tev::events::EventItemCategory&]:
Assertion `this->is_initialized()' failed.
Program received signal SIGABRT, Aborted.
0x0000007f9c105064 in ?? ()
(gdb) bt
#0 0x0000007f9c105064 in ?? ()
#1 0x0000007f9c13c898 in ?? ()
Backtrace stopped: previous frame inner to this frame (corrupt stack?)
(gdb) q
valgrind 输出
==32083== Warning: invalid file descriptor -1 in syscall close()
==32083== at 0x4C8A574: close (in /lib/libpthread-2.25.so)
==32083== by 0x4A24123: setFilename(std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&) (in /opt/ad/lib/libconfiguration.so)
==32083== by 0x4A25A4F: (std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&, std::__cxx11::basic_string<char, std::char
==32083== by 0x4A31FFB: Configuration() (in /opt/ad/lib/libconfiguration.so)
==32083== by 0x5484DF: GetInstance (Singleton.h:80)
==32083== by 0x5484DF: RecordingFactory::RecordingFactory() (RecordingFactory.cpp:18)
==32083== by 0x56D3C7: GetInstance (Singleton.h:39)
==32083== by 0x56D3C7: Service(bool&, std::shared_ptr<tev::events::EventServiceResource> const&, int) (Service.cpp:59)
==32083== by 0x4D391B: ABCService (ABC.h:38)
==32083== by 0x4D391B: void create_service_thread<trc::Service>(std::vector<unsigned long, std::allocator<unsigned long> >&, std::vector<ABCServiceBase*, std::allocator<ABCServiceBase*> >&, bool&,
==32083== by 0x4B3DF7: main (ABC.cpp:140)
/arm/release/usr/include/boost/optional/optional.hpp:1191: boost::optional<T>::reference_type boost::optional<T>::get()
[with T = tev::events::EventItemCategory; boost::optional<T>::reference_type = tev::events::EventItemCategory&]: Assertion `this->is_initialized()' failed.
==32083==
==32083== Process terminating with default action of signal 6 (SIGABRT)
==32083== at 0x63BA064: raise (in /lib/libc-2.25.so)
==32083==
==32083== HEAP SUMMARY:
==32083== in use at exit: 8,217,174 bytes in 9,658 blocks
==32083== total heap usage: 59,869 allocs, 50,211 frees, 13,722,597 bytes allocated
==32083==
==32083== Searching for pointers to 9,658 not-freed blocks
==32083== Checked 104,459,168 bytes
==32083==
==32083== 8 bytes in 1 blocks are still reachable in loss record 1 of 2,795
==32083==
MSVP
#include<iostream>
#include <boost/optional.hpp>
using namespace std;
class Myclass
{
public:
int a;
};
boost::optional<Myclass> func(int a)
{
boost::optional<Myclass> value;
if(a == 0)
{
/* This results in the same runtime error discussed in the question */
value->a = {200};
/* The following #if 0 , if enabled would remove the error */
#if 0
Myclass c;
c.a = 200;
value = c;
#endif
}
return value;
}
int main(int argc, char **argv)
{
boost::optional<Myclass> v = func(0);
if(v)
std::cout << v -> a << std::endl;
else
std::cout << "Uninitialized" << std::endl;
std::cin.get();
return 0;
}
->
运算符的使用仅在optional
初始化时有效。 Boost
决定触发断言失败并中止。
假设 optional
允许您像您尝试的那样修改单个字段。那么它就无法判断该对象是否已完全初始化并且应该被销毁。所以,API让你完全初始化optional
持有的对象,这样当optional
析构时,它知道是否需要销毁持有的对象。
如果您希望 optional
使用默认构造的实例进行初始化,那么您可以在代码中明确说明。
boost::optional<Myclass> value = Myclass();
value->a = 200;
对于您的用例,更直接的方法是简单地 return class 实例,然后初始化 optional
return 值,然后 return boost::none
表示 optional
未初始化。
Myclass c;
if(a == 0)
{
c.a = 200;
return c;
}
return boost::none;