派生自std :: exception的类的赋值运算符
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了派生自std :: exception的类的赋值运算符相关的知识,希望对你有一定的参考价值。
我从std::runtime_error
派生了一个自定义异常类>
静态分析器警告我,如果我定义或删除默认操作(复制ctor,复制/移动运算符,析构函数等。,则应全部定义或删除它们。
为了解决这个愚蠢的警告,我写了丢失的赋值运算符,但是随后又收到另一个警告,即我的运算符隐藏了基本的非虚拟赋值运算符!
由于基类具有私有成员,我无法复制它,看来唯一的解决方案是直接为基对象部分调用基赋值运算符,然后复制其余的*this
对象并最终返回*this
但是在此之前,我先看了基本operator=
的功能以及它的外观:
exception& operator=(exception const& _Other) noexcept if (this == &_Other) return *this; __std_exception_destroy(&_Data); __std_exception_copy(&_Other._Data, &_Data); return *this; private: __std_exception_data _Data; ;
现在知道这是我的实现(带有注释),用于调用基本分配并复制其余的派生对象:
class Exception : public std::runtime_error public: // ... Exception& operator=(const Exception& other) if (this == &other) return *this; // first copy only base class data to *this *dynamic_cast<std::runtime_error*>(this) = runtime_error::operator=( *dynamic_cast<std::runtime_error*>( const_cast<Exception*>(&other))); // then copy derived class data to *this mInfo = other.mInfo; mCode = other.mCode; // finally return complete copy return *this; private: std::error_code mCode; std::string mInfo; ;
这是这样做的正确方法吗?我认为这看起来很麻烦,但我不确定。
编辑
这里是完整的类,以供参考:
#pragma warning (disable : 4275) // base needs to have DLL interface
class ERROR_API Exception :
public std::runtime_error
public:
~Exception() noexcept; // cant be inlined in release build
// default/delete
Exception(const Exception&) = default;
Exception(Exception&&) = delete;
Exception& operator=(const Exception& other)
if (this == &other)
return *this;
// copy base class data to *this
*dynamic_cast<std::runtime_error*>(this) =
runtime_error::operator=(
*dynamic_cast<std::runtime_error*>(
const_cast<Exception*>(&other)));
// copy derived class data to *this
mInfo = other.mInfo;
mCode = other.mCode;
return *this;
Exception& operator=(Exception&&) = delete;
/** Construct from error enum */
template<typename Enum>
Exception(Enum err_enum);
/** Construct from error enum and string*/
template<typename Enum>
Exception(Enum err_enum, String message);
/** Construct from error_code object */
inline Exception(std::error_code err_code);
/** Construct from error_code object and string */
inline Exception(std::error_code err_code, String message);
/** Get error_condidtion name */
inline virtual std::string ConditionName() const;
/** Get error_category name */
inline virtual std::string CategoryName() const;
/** Get error_condition value */
inline virtual int ConditionValue() const noexcept;
/** Get error_condition value */
inline virtual int ErrorValue() const noexcept;
/** Get additional information string passed to constructor */
inline virtual const String& GetInfo() const noexcept;
/** Get error_code object associated with this exception object */
inline virtual const std::error_code& code() const noexcept;
private:
SUPPRESS(4251); // member needs to have DLL interface
std::error_code mCode;
SUPPRESS(4251); // member needs to have DLL interface
String mInfo;
;
#pragma warning (default : 4275) // base needs to have DLL interface
我从std :: runtime_error静态分析器派生了一个自定义异常类,警告我,如果我定义或删除默认操作(复制ctor,复制/移动运算符,析构函数等。,我...
答案
感谢Ulrich Eckhardt,Peter和其他人的好评,这是我的工作方式,结果完全没有警告:
class Exception : public std::runtime_error
public:
~Exception() noexcept; // can't be inlined in release build (defaulted in source)
// default/delete
Exception(const Exception&) = default;
Exception(Exception&&) = default;
Exception& operator=(const Exception&) noexcept = default;
Exception& operator=(Exception&&) noexcept(false) = deault;
// the rest of the code ...
;
以上是关于派生自std :: exception的类的赋值运算符的主要内容,如果未能解决你的问题,请参考以下文章
C++:当包含从类模板派生的类的标头时,编译器警告 C4505