summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/sql/drivers/psql/qsql_psql.cpp42
-rw-r--r--tests/auto/sql/kernel/qsqlquery/tst_qsqlquery.cpp36
2 files changed, 63 insertions, 15 deletions
diff --git a/src/sql/drivers/psql/qsql_psql.cpp b/src/sql/drivers/psql/qsql_psql.cpp
index c83c633fd0..3aa2455ff0 100644
--- a/src/sql/drivers/psql/qsql_psql.cpp
+++ b/src/sql/drivers/psql/qsql_psql.cpp
@@ -1248,6 +1248,23 @@ QSqlRecord QPSQLDriver::record(const QString& tablename) const
return info;
}
+template <class FloatType>
+inline void assignSpecialPsqlFloatValue(FloatType val, QString *target)
+{
+ if (isnan(val)) {
+ *target = QLatin1String("'NaN'");
+ } else {
+ switch (isinf(val)) {
+ case 1:
+ *target = QLatin1String("'Infinity'");
+ break;
+ case -1:
+ *target = QLatin1String("'-Infinity'");
+ break;
+ }
+ }
+}
+
QString QPSQLDriver::formatValue(const QSqlField &field, bool trimStrings) const
{
Q_D(const QPSQLDriver);
@@ -1255,7 +1272,7 @@ QString QPSQLDriver::formatValue(const QSqlField &field, bool trimStrings) const
if (field.isNull()) {
r = QLatin1String("NULL");
} else {
- switch (field.type()) {
+ switch (int(field.type())) {
case QVariant::DateTime:
#ifndef QT_NO_DATESTRING
if (field.value().toDateTime().isValid()) {
@@ -1305,21 +1322,16 @@ QString QPSQLDriver::formatValue(const QSqlField &field, bool trimStrings) const
qPQfreemem(data);
break;
}
- case QVariant::Double: {
- double val = field.value().toDouble();
- if (isnan(val))
- r = QLatin1String("'NaN'");
- else {
- int res = isinf(val);
- if (res == 1)
- r = QLatin1String("'Infinity'");
- else if (res == -1)
- r = QLatin1String("'-Infinity'");
- else
- r = QSqlDriver::formatValue(field, trimStrings);
- }
+ case QMetaType::Float:
+ assignSpecialPsqlFloatValue(field.value().toFloat(), &r);
+ if (r.isEmpty())
+ r = QSqlDriver::formatValue(field, trimStrings);
+ break;
+ case QVariant::Double:
+ assignSpecialPsqlFloatValue(field.value().toDouble(), &r);
+ if (r.isEmpty())
+ r = QSqlDriver::formatValue(field, trimStrings);
break;
- }
default:
r = QSqlDriver::formatValue(field, trimStrings);
break;
diff --git a/tests/auto/sql/kernel/qsqlquery/tst_qsqlquery.cpp b/tests/auto/sql/kernel/qsqlquery/tst_qsqlquery.cpp
index 9502343bd7..d2b4474dd4 100644
--- a/tests/auto/sql/kernel/qsqlquery/tst_qsqlquery.cpp
+++ b/tests/auto/sql/kernel/qsqlquery/tst_qsqlquery.cpp
@@ -34,6 +34,8 @@
#include <QtTest/QtTest>
#include <QtSql/QtSql>
+#include <numeric>
+
#include "../qsqldatabase/tst_databases.h"
const QString qtest(qTableName("qtest", __FILE__, QSqlDatabase()));
@@ -159,6 +161,8 @@ private slots:
void bindBool();
void psql_bindWithDoubleColonCastOperator_data() { generic_data("QPSQL"); }
void psql_bindWithDoubleColonCastOperator();
+ void psql_specialFloatValues_data() { generic_data("QPSQL"); }
+ void psql_specialFloatValues();
void queryOnInvalidDatabase_data() { generic_data(); }
void queryOnInvalidDatabase();
void createQueryOnClosedDatabase_data() { generic_data(); }
@@ -2437,6 +2441,38 @@ void tst_QSqlQuery::psql_bindWithDoubleColonCastOperator()
QCOMPARE( q.executedQuery(), QString( "select sum((fld1 - fld2)::int) from " + tablename + " where id1 = 1 and id2 =2 and id3=3" ) );
}
+void tst_QSqlQuery::psql_specialFloatValues()
+{
+ if (!std::numeric_limits<float>::has_quiet_NaN)
+ QSKIP("Platform does not have quiet_NaN");
+ if (!std::numeric_limits<float>::has_infinity)
+ QSKIP("Platform does not have infinity");
+
+ QFETCH( QString, dbName );
+ QSqlDatabase db = QSqlDatabase::database( dbName );
+
+ CHECK_DATABASE( db );
+ QSqlQuery query(db);
+ const QString tableName = qTableName("floattest", __FILE__, db);
+ QVERIFY_SQL( query, exec("create table " + tableName + " (value float)" ) );
+ QVERIFY_SQL(query, prepare("insert into " + tableName + " values(:value)") );
+
+ QVariantList data;
+ data << QVariant(double(42.42))
+ << QVariant(std::numeric_limits<double>::quiet_NaN())
+ << QVariant(std::numeric_limits<double>::infinity())
+ << QVariant(float(42.42))
+ << QVariant(std::numeric_limits<float>::quiet_NaN())
+ << QVariant(std::numeric_limits<float>::infinity());
+
+ foreach (const QVariant &v, data) {
+ query.bindValue(":value", v);
+ QVERIFY_SQL( query, exec() );
+ }
+
+ QVERIFY_SQL( query, exec("drop table " + tableName) );
+}
+
/* For task 157397: Using QSqlQuery with an invalid QSqlDatabase
does not set the last error of the query.
This test function will output some warnings, that's ok.