On 21/07/2023 11:01, Volker Hilsheimer via Development wrote:
How about conversion:

I, for one, would like to stop seeing magic conversions added into QVariant, and keep breaking stuff at every Qt major release because we realize we went overboard and have to remove features.


Now, one could think of folding QVariant and std::optional nullability semantics, but this becomes hairy very very quick. Take this:


  std::optional<int> opt; // nullopt
  QVariant v = QVariant::fromValue(opt);

Is `v` a null QVariant with Int metatype, or a valid variant with a std::optional<int> metatype loaded with a copy of the optional? What if `opt` is loaded instead?

Bonus question: this works *today*, and guess what it does?


So this at a minimum is a different named constructor: QVariant::fromStdOptional or similar. This doesn't help at all in generic code (e.g. in the property system) -- when is one supposed to unwrap an optional vs keep it wrapped?


     QVariant(std::optional<T>>).value<U>(); // return U{} if T cannot be 
converted; otherwise U(T);

This isn't how QVariant works today for `QVariant::fromValue(T{}).value<U>()`, unless T and U are a specific combination of types in a whitelist of sorts, or have a custom conversion registered; so, if anything, it should follow the same semantics: refuse the conversion, unless it's special or registered. And by "registered" I mean registered from `std::optional<T>` to `U`, not from `T` to `U`.



     QVariant().value<std::optional<T>>(); // nullopt, not a std::optional 
holding a T{}
     QVariant(42).value<std::optional<int>>(); // std::optional holding 42
     QVariant(QSize()).value<std::optional<int>>(); // probably nullopt?

All of these already have established semantics. We can't change them without breaking API. We need an `optionalValue<T>()` accessor or something like that (again, that kills the idea of using this in generic code, properties, etc.).

QVariant().value<std::optional<T>>();

Returns default-constructed std::optional<T> (i.e. nullopt)

QVariant(42).value<std::optional<int>>(); // std::optional holding 42

No, returns nullopt, types don't match and not in the list of magical conversions (and we can't extend such a list because it's an API break)

QVariant(QSize()).value<std::optional<int>>();

Nullopt again (types don't match).


My 2 c,
--
Giuseppe D'Angelo | giuseppe.dang...@kdab.com | Senior Software Engineer
KDAB (France) S.A.S., a KDAB Group company
Tel. France +33 (0)4 90 84 08 53, http://www.kdab.com
KDAB - The Qt, C++ and OpenGL Experts

Attachment: smime.p7s
Description: S/MIME Cryptographic Signature

-- 
Development mailing list
Development@qt-project.org
https://lists.qt-project.org/listinfo/development

Reply via email to