[optional] Breaking changes in 1.33.0 vs 1.32.0

I have some code that has been merrily using the 1.32.0 release of boost, including boost::optional, and I've just tried to change to use the 1.33.0 release (this is the first change to this codebase since 1.33.0 was released). In my code, I have boost::optional<X> where X is copy-constructible, but not assignable. This works in 1.32.0, but fails in 1.33.0. Ouch! What is the reason for the change? Why is this not listed in the "Updated libraries" section of the docs? Why is this not listed under the "Type Requirements" section of the docs? Anthony -- Anthony Williams Software Developer Just Software Solutions Ltd http://www.justsoftwaresolutions.co.uk

I have some code that has been merrily using the 1.32.0 release of boost, including boost::optional, and I've just tried to change to use the 1.33.0 release (this is the first change to this codebase since 1.33.0 was released).
In my code, I have boost::optional<X> where X is copy-constructible, but not assignable. This works in 1.32.0, but fails in 1.33.0. Ouch!
Oh boy.
What is the reason for the change?
I need to dig up the archives to recall the exact reason... I do remeber though that there was a good one. As for the _justification_ for a breaking change, the idea was that if X is non-assignable, then optional<X> should not be assignable either, or at the very least, you don't need it to be assignable. That is, you can always write: optional<X> o ; o = none ; o = v; instead of just o = v ; if X is non-assignable. Anyway, don't you agree that optional<X>::operator= should go through X::operator=? And in that case, is there a choice but to have optional assignment fail with non-assignable types?
Why is this not listed in the "Updated libraries" section of the docs?
Becuase I failed to list it there.
Why is this not listed under the "Type Requirements" section of the docs?
Because I forgot to add it. The specific docs for operator= do mention that T's operator = is used; but you're right I forgot to update the requirements. Anyway, does the "reset it first" trick work for you? Do you think this change has to be rolled back (just asking)? Best, -- Fernando Cacciola SciSoft http://fcacciola.50webs.com/

"Fernando Cacciola" <fernando_cacciola@hotmail.com> writes:
I have some code that has been merrily using the 1.32.0 release of boost, including boost::optional, and I've just tried to change to use the 1.33.0 release (this is the first change to this codebase since 1.33.0 was released).
In my code, I have boost::optional<X> where X is copy-constructible, but not assignable. This works in 1.32.0, but fails in 1.33.0. Ouch!
Oh boy.
struct X { const int a; X(int a_): a(a_) {} X(const X& other): a(other.a) {} }; is an example of a type with this property.
What is the reason for the change?
I need to dig up the archives to recall the exact reason... I do remeber though that there was a good one. As for the _justification_ for a breaking change, the idea was that if X is non-assignable, then optional<X> should not be assignable either, or at the very least, you don't need it to be assignable. That is, you can always write:
optional<X> o ; o = none ; o = v;
instead of just
o = v ;
if X is non-assignable.
Except that doesn't work in my case, since X doesn't have a valid operator=, so the assignment fails to compile.
Anyway, don't you agree that optional<X>::operator= should go through X::operator=? And in that case, is there a choice but to have optional assignment fail with non-assignable types?
I'm not sure I agree that optional<X>::operator= should use X::operator=, but I can see the logic. Given that, you have no choice but for assignment to fail to compile if X doesn't have an operator=, unless you can have a trait somewhere that means the code that uses X::operator= is not compiled for classes that don't have an operator=.
Anyway, does the "reset it first" trick work for you? Do you think this change has to be rolled back (just asking)?
Looking at the code for optional, everything is built on top of assignment --- reset uses assign, for example. This needs to be rethought before it is at all usable with my code (even if I explicitly use reset rather than assignment). As a workaround, I could write an operator= that throws, but it's a bit of a nasty hack. Anthony -- Anthony Williams Software Developer Just Software Solutions Ltd http://www.justsoftwaresolutions.co.uk
participants (2)
-
Anthony Williams
-
Fernando Cacciola