Re: Onwards and upwards
On Thursday, 2 April 2015 07:51:11 UTC+3, woodb...@gmail.com wrote:
What do you think of this class?
Average class.
class failure : public ::std::exception {
::std::string whatStr;
public:
explicit failure (char const* w) : whatStr(w) {}
Can use alternative syntax 'char const s[]' to indicate that C string
is expected.
explicit failure (::std::string w) : whatStr(::std::move(w)) {}
~failure () throw() {}
Feels pointless to indicate 'noexcept' here since compiler can see it
itself. You can indicate that destructor is default and virtual like:
virtual ~failure() = default;
However since you do not define neither assignments nor
copy-constructions of 'failure' it feels better to remove the
destructor as well by rule of zero.
char const* what () const throw()
{ return whatStr.c_str(); }
Can indicate that member function is virtual override (with keywords
'virtual' and 'override').
failure& operator<< (char const* s)
{
whatStr.append(s);
return *this;
}
failure& operator<< (char* s)
{
whatStr.append(s);
return *this;
}
That looks unneeded overload; its body is identical to previous overload.
failure& operator<< (::std::string const& s)
{
whatStr.append(s);
return *this;
}
template <class T>
failure& operator<< (T val)
{
whatStr.append(::std::to_string(val));
return *this;
}
Can use:
using std::to_string;
whatStr.append(to_string(val));
That will consider likely 'to_string's from T's namespace in name lookup.
};
I'm thinking about changing it to something like this:
class failure : public ::std::string {
public:
explicit failure (char const* w) : std::string(w) {}
explicit failure (::std::string w) : std::string(::std::move(w)) {}
~failure () throw() {}
template <class T>
failure& operator<< (T val)
{
this->append(::std::to_string(val));
return *this;
}
};
Some preliminary tests show smaller executable sizes with
this second approach.
Technically it is 'catch (std::string const&)' for user?
Performance considerations are always less important than usability
considerations so I usually derive exception types that may be
thrown out of my code from 'std::runtime_error'. Better usability
for caller, microscopic difference in performance.
If you really need such microscopic performance benefits then better
throw enwrapped into 'std::exception' string literals or integers.
IOW do not build long texts at throw site. For example: If catch
site can't do anything with long text that explains in detail what
strange byte sequence did not let a parser to parse the input,
then do not build such thing at throw site and executable size is
immediately smaller too.