Boost logo

Boost :

Subject: Re: [boost] [outcome] Requesting pre-review of Boost.Outcome tutorial
From: Niall Douglas (s_sourceforge_at_[hidden])
Date: 2016-11-12 03:53:43


On 11 Nov 2016 at 23:33, Klemens Morgenstern wrote:

> I just had another idea (I hope I didn't miss that): it would be awesome
> if there was some way to deal with objects, that might have an errornous
> state. I.e. something like that:
>
> outcome<path> p1("-invälid#value"); //error set
>
> outcome<path> p2("valid-value"); //not set
> int i = p2->something_errornous(); //now I have a set error.
>
> I'm not sure how to do that, but maybe something like this: the ctor
> checks through std::is_nothrow_constructible if the last argument can be
> std::error_code or
> something like that and then takes this one to capture the error;
> elsewise it catches the exception.
>
> And for the member-functions you could use some indirect call, like this:
>
> p2.invoke(&path::something_errornous);
>
> Which then calls the matching function with an std::error_code or the
> exception. I'm not sure if that should return outcome<int> or int and
> put the error into p2.
>
> This would be useful for a library, which uses the std::error_code or
> exception pattern, because it could be integrated with your library very
> convienently.

I'm not sure if I understood you correctly, but you might be wanting
to do pattern matching based on the contents.

Outcome has that, so:

outcome.match(callable) will call the appropriate overload of
callable(T | error_code | exception_ptr). This is very handy.

We can also do monadic bind on the state e.g.

outcome >> [](error_code){ /* only called if outcome contains an
error_code. We can return a new type of outcome here used by
subsequent bind operators i.e. we can be an error_code
filter/converter */ };

There are also operators:

outcome<int> | 4; // If outcome is empty, errored or excepted,
return outcome<int>(4)

outcome<int> & 5; // If outcome has value, return outcome<int>(5)

If however you were talking about tombstone values i.e. special
values of T with special meaning, Outcome does not currently provide
that but could be extended to do so by someone who isn't me very
easily (pull requests welcome). SG14 already were interested in an
Outcome with packed state using tombstones to reduce storage size,
Outcome does already store bools and void and all outcome state into
a single packed byte when possible.

> > I would add that it should be the case that if properly used Outcome
> > never throws an exception, not ever. Therefore it should never
> > terminate the process.
> >
> > One thing I'll add before peer review is an optional facility that it
> > will cause a link error if your code ever could cause an exception to
> > throw. This should aid debugging.
>
> Intersting, how would that work? And if I disable exceptions
> (-fno-exceptions) I'd already get an error.

I'll probably use the preprocessor to mangle together a location
identifying extern function declaration which I call in a throw but
doesn't exist. Under optimisation, the compiler will elide all such
calls as being unreachable code and thus the program links
successfully. If any could be called, the program will fail to link.
I've implemented this before in other projects, it works fine on all
the major compilers but needs to not be defaulted on as it confuses
the hell out of most end users.

Niall

-- 
ned Productions Limited Consulting
http://www.nedproductions.biz/ 
http://ie.linkedin.com/in/nialldouglas/

Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk