2014-11-18 22:35 GMT+01:00 Vladimir Batov
In
that case why not add it to the regular optional?
IMHO, in order to introduce an alternative component, there should be significant and incompatible design and interface differences between the two. So far I don't see the need for such differences.
As explained above: serious backwards incompatibility. Unacceptable by many, including myself.
I have to admit I find it somewhat of a concern hearing from the "optional" maintainer and someone leading "optional" for standardization that he does not seem to share/agree with the current "optional" design to the point where you are keen on forking a "seriously incompatible" variant. Going ahead with the latter will be a lot of effort implementing, promoting, educating, defending... IMO that'll be the effort 1) not necessarily successful; 2) fragmenting the user-base; 3) most importantly, it'll be the effort taken *away* from the current "optional"... which seems so close (hopefully) to standardization. If you have concerns (you would not initiate the conversation if you did not), let's discuss them within the "optional" boundaries and document/justify the decisions made. Do I worry too much?
Ok, this concern deserves a clarification from my part. I am more than satisfied with the current design of both boost::optional and std::optional. i find the decisions right. The direct (unchecked) access to the contained value is essential. The conversion from T may not be critically essential but is very useful. My motivation is NOT the dissatisfaction with the current interface. You are right that by starting this thread I might have been sending the opposite message. Therefore I am declaring my position and motivation here explicitly. It is simply that I observe and acknowledge the expectations of a portion of the community to have a different interface. I also acknowledge that having two interfaces for nearly the same thing may be a bad idea in itself. This is why I am simply discussing (talking) and not taking any actions. I want to hear others' input. And I find yours particularly valuable. Note that the interface I am proposing is not just fool-proof. It is designed in a way that forces you to express your intentions rather that just giving orders. The safety is not achieved by just prohibiting things but by forcing you to rethink what you are doing. To some extent, I consider Boost an incubator of ideas rather than "the standard way of doing things". I would agree that having two optionals in STD would be a bad message. This is less so for Boost. We would have people experiment with an alternative and decide which they find better, and they could deliver their opinion to the Standardization committee. Andrzej,
On 11/18/2014 08:23 PM, Andrzej Krzemienski wrote:
... And to remove operator* and get() and value() and get_pointer() - anything that could cause UB. And remove implicit conversion from T
1. I might be open to the idea of unifying/cleaning the access interface and settling on one... but taking them *all* out?.. Or you want to keep operator->()? Then, I still can do
optional<T> ot; T* t = ot.operator->();
You might say, it's crazy. My point is that if you want to save me (the user) from myself with "safe optional", you are most likely wasting your effort -- an uneducated idiot will always find a way to hurt himself.
Note that my intention is not to remove these from boost::optional, but to provide a second type that does not have them. This is not affecting you: you will stick to boost::optional interface which remains unchanged. Yes, in the new hypothetical I would be also removing operator-> No unchecked access. Yes, I do acknowledge that direct unchecked access is necessary (e.g., for performance reasons). It is only for the people that are determined to use the alternate interface and are willing to pay the cost.
2. I find it troubling that you keep bringing "remove implicit conversion from T " up. That indicates that the property is close to the top of your "grievances" list. On my side, I find that implicit conversion essential for sane interactions of users with "optional". Back a while, when we were discussing "optional" (was it ISO forum?), I remember Fernando Cacciola expressing the same opinion (and as strongly). I'd greatly appreciate if you could please provide practical usage/deployment examples where implicit conversion from T causes a problem.
optional<double> Aircraft::weight() { if (Impl* impl = get_impl()) return impl->compute_weight(); else return none; } double Aircraft::max_weight() { return 10000.0; } bool too_heavy(Aircraft& ac) { return ac.weight() > ac.max_weight(); // in "safe" optional compiler would spot the bug } This example only tells me that there exist some use cases where conversion from T is dangerous/unintended/surprising. I DO NOT conclude that it should have never been added. Regards, &rzej