Russian Qt Forum
Ноябрь 24, 2024, 04:55 *
Добро пожаловать, Гость. Пожалуйста, войдите или зарегистрируйтесь.
Вам не пришло письмо с кодом активации?

Войти
 
  Начало   Форум  WIKI (Вики)FAQ Помощь Поиск Войти Регистрация  

Страниц: [1]   Вниз
  Печать  
Автор Тема: QVariant NULL == 0?  (Прочитано 8416 раз)
EhTemka
Гость
« : Декабрь 04, 2008, 12:34 »


Всем привет.

Qt 4.2.3

Вот такой код :

Код
C++ (Qt)
       QVariant varNull(QVariant::Double);
QVariant var0 = 0.0;
if (varNull == var0) {
EH_COUT2("varNull.isNull()", varNull.isNull())EH_ENDL; // мои макросы для вывода в стандартный поток
EH_COUT2("var0.isNull()", var0.isNull())EH_ENDL;
}
 

вывод :
varNull.isNull()  1
var0.isNull()     0

То есть внутрь if заходит.

Столкнулся я с этим при работе с базой. Есть в одной таблице поле типа double,
где могут быть любые значения, в том числе 0. А могут быть и не заданы, что имеет свой смысл.
Запрос всё возвращает правильно, т.е. если 0, то 0 и query.value(i) не isNull; если не задано, то query.value(i) - isNull.
И в некоторых местах программы мне надо сравнивать эти значения. И вот собственно натыкаюсь на то, что 0 и нету оказывается одно и тоже, что в контексте моей программы недопустимо. То есть конечно дополнительные проверки всё разрешают, но...

Вопрос к гуру. Является ли это багом, или я что-то не понимаю?


« Последнее редактирование: Декабрь 04, 2008, 16:17 от pastor » Записан
Rcus
Гость
« Ответ #1 : Декабрь 04, 2008, 12:40 »

Код
C++ (Qt)
bool QVariant::cmp(const QVariant &v) const
{
   QVariant v2 = v;
   if (d.type != v2.d.type) {
       if (qIsNumericType(d.type) && qIsNumericType(v.d.type)) {
           if (qIsFloatingPoint(d.type) || qIsFloatingPoint(v.d.type))
               return qFuzzyCompare(toDouble(), v.toDouble());
           else
               return toLongLong() == v.toLongLong();
       }
       if (!v2.canConvert(Type(d.type)) || !v2.convert(Type(d.type)))
           return false;
   }
   return handler->compare(&d, &v2.d);
}
 
Помоему все нормально.
Записан
EhTemka
Гость
« Ответ #2 : Декабрь 04, 2008, 13:09 »

Цитировать
Помоему все нормально.

Что вы имеете ввиду?

в функции что ты привел в моем случае срабатывает
Код:
return handler->compare(&d, &v2.d);

и возвращает true.

Это нормально?

P.S. А как вы создаете такой красивый код в сообщении?
« Последнее редактирование: Декабрь 04, 2008, 13:15 от EhTemka » Записан
kirill
Гость
« Ответ #3 : Декабрь 04, 2008, 13:29 »

GeShi - комбобокс при ответе - используй его.
Код
C++ (Qt)
 
Записан
Rcus
Гость
« Ответ #4 : Декабрь 04, 2008, 15:45 »

собственно говоря если вам нужно пустое значение double, то почему бы не воспользоваться
Код
C++ (Qt)
std::numeric_limits<double>::quiet_NaN();
Записан
EhTemka
Гость
« Ответ #5 : Декабрь 05, 2008, 11:06 »

Вопрос не в том, что делать, А в том что является ли это багом или нет (всмысле репортить ли троллям).

Ведь к примеру делегат понимает, где нул а где ноль, то есть для него разница есть, а при сравнении получается что нет..
Записан
Rcus
Гость
« Ответ #6 : Декабрь 05, 2008, 11:48 »

Код
C++ (Qt)
QVariant(0.0)==QVariant(QVariant::Double)
QVariant(0.0).toDouble()==QVariant(QVariant::Double).toDouble()

Я бы очень удивился если бы эти выражения давали разный результат Улыбающийся
Записан
ритт
Гость
« Ответ #7 : Декабрь 05, 2008, 12:01 »

это не баг.
в первом случае ты инициализируешь вариант пустым значением - в итоге получаешь типизированный вариант с неопределённым значением, а isNull() возвращает правду;
во втором случае ты инициализируешь вариант конкретным значением - в итоге isNull() возвращает ложь, т.к. вариант типизирован и определён.
Записан
BRE
Гость
« Ответ #8 : Декабрь 05, 2008, 12:15 »

Я так понял, что EhTemka интересует почему QVariant::null равен QVariant::0.
Сейчас тоже сам задумался... Непонимающий
Записан
Tonal
Гость
« Ответ #9 : Декабрь 05, 2008, 12:43 »

А что возвернёт конструкция QVariant("0") == QVariant(0)?
Или QVariant(0.0) == QVariant(0)?

Если true, то с null-ом поведение вполне логично. Улыбающийся
Записан
EhTemka
Гость
« Ответ #10 : Декабрь 05, 2008, 13:03 »

И все - таки мне кажется

Цитировать
типизированный вариант с неопределённым значением
НЕ должен равняться  типизированному варианту с заданным значением. А 0.0 - это заданное значение...
Записан
ритт
Гость
« Ответ #11 : Декабрь 06, 2008, 04:58 »

при доступе к значению неопределённый вариант кастит значение к дефолтовуму пустому, но при этом остаётся пустым (isNull() == true)
сравниваешь 0.0 и 0.0 - чего ожидаешь?
Записан
EhTemka
Гость
« Ответ #12 : Декабрь 06, 2008, 15:20 »

Я ожидал более разумного поведения оператора сравнения у QVariant. Сейчас мне приходится делать дополнительные проверки на null перед тем как производить сравнение, т.е. этот код мог бы вполне быть внутри оператора. Я в первом посте привел пример, когда null(незадано) и ноль разные по смыслу и считаю это (null != 0) вполне логичным. Если isNull == true, то должно быть все равно, какое значение у второго сравниваемого элемента, возвращать false (если он конечно не isNull тоже). Ведь я сравниваю не даблы а варианты. И QVariant, имхо, должен это понимать и кастить значение при сравнении в последнюю очередь, когда все остальные условия проверены.
Записан
Rcus
Гость
« Ответ #13 : Декабрь 06, 2008, 15:34 »

Ну если вам так хочется чтобы в вашем коде было различие между null и 0 вариантами то сделайте себе инлайн функцию сравнения с дополнительной проверкой.
В Qt такое тащить помоему смысла нет (попробуйте проверить, будет ли сама библиотека работать если в оператор сравнения вставить проверку isNull), да и слишком много стороннего кода зависит от данного поведения.
Записан
Страниц: [1]   Вверх
  Печать  
 
Перейти в:  


Страница сгенерирована за 0.412 секунд. Запросов: 21.