I'm having trouble understanding the behaviour of QVariant::canConvert
and QVariant::toDouble
. I'd expect that both of these would return false if the underlying variant data is, say, a QString
, but I'm getting different results as shown:
#include <QString>
#include <QVariant>
#include <QDebug>
int main(int argc, char *argv[])
{
QString not_a_number("foo");
QVariant variant(not_a_number);
auto can_convert_1 = variant.canConvert<double>();
auto can_convert_2 = false;
variant.toDouble(&can_convert_2);
qDebug() << can_convert_1 << can_convert_2; //prints: true false
}
The method canConvert
returns true whereas the toDouble
return false.
Can someone explain this behaviour please?
I'm using Qt 5.15.7 on Windows with Visual Studio 2019.
double QVariant::toDouble(bool *ok = nullptr) const
and
template <typename T> bool QVariant::canConvert() const
have two very different meanings. bool* ok
will return true if the conversion has actually succeded, while canConvert()
tell if the source type could be converted to the destination type.
QString
can be converted to double
? Maybe.
QString
is one of the type allowed to be converted to double? Yes, so canConvert()
will always return true
, but toDouble()
of course will fail.
Indeed if you try
auto convert = [](auto&& string){
QString not_a_number(string);
QVariant variant(not_a_number);
auto can_convert_1 = variant.canConvert<double>();
auto can_convert_2 = false;
variant.toDouble(&can_convert_2);
qDebug() << can_convert_1 << can_convert_2;
};
convert("foo");
convert("5");
will print
true false
true true
Both are QString, so canConvert succed, toDouble only succed for "5" can actually be converted to double.