|
Boost : |
Subject: Re: [boost] [optional] generates unnessesary code for trivial types
From: Domagoj Saric (domagoj.saric_at_[hidden])
Date: 2012-02-09 07:45:49
On 7.2.2012. 22:36, Hite, Christopher wrote:
> I tested the techniques I would use to improve optional. So I think I can
> deliver this very small set of goals cleanly:
>
> 1) ~optional doesn't set m_initialized.
>
> 2) has_trivial_destructor<T> implies has_trivial_destructor<optional<T> >
>
> 3) has_has_trivial_copy<T> and has_trivial_assign<T> implies them optional
> unless sizeof(T) exceeds some constant max_trivial_copy_Size, which
> can also be overridden.
>
> 4) I'll define a optional_traits<T> with defaults and an
> optional_with_traits<T,Traits=optional_traits<T> >
> which can be used to make optionals which override features and from which
> optional<T> will derive. That's the best compromise if I can't change
> the signature of optional (Is Robert Stewart right?). I think we should use
> the traits technique for any new libraries.
>
> Thanks Sebastian Redl and Domagoj Saric for pointing out that (2) and (3)
> will may help some compilers put cheap optionals in registers.
>
> Shall I continue? Should I make branch or do it in trunk?
The optional in sandbox (that passes regression tests) already does 1 and 2
(among many other things) so doing it from scratch again would be reinventing
the wheel.
ad 3) I would agree to such a compromise: that a bool be used for small PODs (so
that they get trivial copy and assign) and a pointer for everything else (so
that these get a no-op get_ptr() and nice debugging)...
[In my version PODs always/implicitly get "nice debugging" regardless of the
lifetime management implementation (bool/pointer/...).]
ad 4) As said before, even though my personal prima facie stance is always "the
more configurability the better", it is highly unlikely (from reasons previously
given) that changing optional's signature would pass.
Given that, the best workaround IMO for such "ancient"/"written in stone"
constructs that suffer from the "Joe Sixpack" approach, i.e. they are good
enough for 90% use cases, is to:
- create a separate configurable construct and use it as an implementation
detail of the original construct that maximally auto-configures based on T
(improving the "good enough percentage" to "98%")
- provide global configuration (that overrides auto-configuration) for the
original construct (improving the "good enough percentage" to "99.8%")
...and the remaining "0.2%" can use the new construct directly...
So far this corresponds to your optional_with_traits approach except that I
don't think that providing global configuration by overriding/specializing the
default traits is the correct approach. As you noted, this can violate the ODR
and AFAIK users are not used that changing a _type_ can violate the ODR and
change the behaviour of another type. I'd rather use macros for that (e.g.
#define BOOST_OPTIONAL_MAX_BRANCHLESS_COPY_SIZE 4 * sizeof( void * )) because
programmers are already used/"trained" to be careful with macros WRT to the ODR
_and_ because there already exist tools/compilers which can detect macro ODR
violations at link time (e.g. MSVC10)...
-- "What Huxley teaches is that in the age of advanced technology, spiritual devastation is more likely to come from an enemy with a smiling face than from one whose countenance exudes suspicion and hate." Neil Postman
Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk