Use same-msecs optimization more in QDateTime comparison
QDateTime's comparisons just compare milliseconds when both values are local times and their statuses (hence DST-ness) match. It can do the same for time-zones. While doing the same for UTC and fixed offsets wins nothing, it also costs nothing, given that we're already checking the spec. Task-number: QTBUG-75585 Change-Id: Ib6d824569aba8def2f1319ef3a11cca6869a5b5e Reviewed-by: Thiago Macieira <thiago.macieira@intel.com>bb10
parent
691762e0e3
commit
3bd6901429
|
|
@ -2763,6 +2763,37 @@ static inline Qt::TimeSpec getSpec(const QDateTimeData &d)
|
|||
return extractSpec(getStatus(d));
|
||||
}
|
||||
|
||||
/* True if we *can cheaply determine* that a and b use the same offset.
|
||||
If they use different offsets or it would be expensive to find out, false.
|
||||
Calls to toMSecsSinceEpoch() are expensive, for these purposes.
|
||||
See QDateTime's comparison operators.
|
||||
*/
|
||||
static inline bool usesSameOffset(const QDateTimeData &a, const QDateTimeData &b)
|
||||
{
|
||||
const auto status = getStatus(a);
|
||||
if (status != getStatus(b))
|
||||
return false;
|
||||
// Status includes DST-ness, so we now know they match in it.
|
||||
|
||||
switch (extractSpec(status)) {
|
||||
case Qt::LocalTime:
|
||||
case Qt::UTC:
|
||||
return true;
|
||||
|
||||
case Qt::TimeZone:
|
||||
/* TimeZone always determines its offset during construction of the
|
||||
private data. Even if we're in different zones, what matters is the
|
||||
offset actually in effect at the specific time. (DST can cause things
|
||||
with the same time-zone to use different offsets, but we already
|
||||
checked their DSTs match.) */
|
||||
case Qt::OffsetFromUTC: // always knows its offset, which is all that matters.
|
||||
Q_ASSERT(!a.isShort() && !b.isShort());
|
||||
return a->m_offsetFromUtc == b->m_offsetFromUtc;
|
||||
}
|
||||
Q_UNREACHABLE();
|
||||
return false;
|
||||
}
|
||||
|
||||
#if QT_CONFIG(timezone)
|
||||
void QDateTimePrivate::setUtcOffsetByTZ(qint64 atMSecsSinceEpoch)
|
||||
{
|
||||
|
|
@ -4333,7 +4364,7 @@ bool QDateTime::operator==(const QDateTime &other) const
|
|||
if (!other.isValid())
|
||||
return false;
|
||||
|
||||
if (getSpec(d) == Qt::LocalTime && getStatus(d) == getStatus(other.d))
|
||||
if (usesSameOffset(d, other.d))
|
||||
return getMSecs(d) == getMSecs(other.d);
|
||||
|
||||
// Convert to UTC and compare
|
||||
|
|
@ -4365,7 +4396,7 @@ bool QDateTime::operator<(const QDateTime &other) const
|
|||
if (!other.isValid())
|
||||
return false;
|
||||
|
||||
if (getSpec(d) == Qt::LocalTime && getStatus(d) == getStatus(other.d))
|
||||
if (usesSameOffset(d, other.d))
|
||||
return getMSecs(d) < getMSecs(other.d);
|
||||
|
||||
// Convert to UTC and compare
|
||||
|
|
|
|||
|
|
@ -1971,12 +1971,26 @@ void tst_QDateTime::operator_eqeq_data()
|
|||
// might agree with UTC about the epoch, all the same.
|
||||
|
||||
QTest::newRow("invalid == invalid") << QDateTime() << QDateTime() << true << false;
|
||||
QTest::newRow("invalid == valid #1") << QDateTime() << dateTime1 << false << false;
|
||||
QTest::newRow("invalid != valid #1") << QDateTime() << dateTime1 << false << false;
|
||||
|
||||
if (zoneIsCET) {
|
||||
QTest::newRow("data14") << QDateTime(QDate(2004, 1, 2), QTime(2, 2, 3), Qt::LocalTime)
|
||||
<< QDateTime(QDate(2004, 1, 2), QTime(1, 2, 3), Qt::UTC) << true << true;
|
||||
QTest::newRow("data14")
|
||||
<< QDateTime(QDate(2004, 1, 2), QTime(2, 2, 3), Qt::LocalTime)
|
||||
<< QDateTime(QDate(2004, 1, 2), QTime(1, 2, 3), Qt::UTC) << true << true;
|
||||
QTest::newRow("local-fall-back") // Sun, 31 Oct 2004, 02:30, both ways round:
|
||||
<< QDateTime::fromMSecsSinceEpoch(Q_INT64_C(1099186200000))
|
||||
<< QDateTime::fromMSecsSinceEpoch(Q_INT64_C(1099182600000))
|
||||
<< false << false;
|
||||
}
|
||||
#if QT_CONFIG(timezone)
|
||||
const QTimeZone CET("Europe/Oslo");
|
||||
if (CET.isValid()) {
|
||||
QTest::newRow("CET-fall-back") // Sun, 31 Oct 2004, 02:30, both ways round:
|
||||
<< QDateTime::fromMSecsSinceEpoch(Q_INT64_C(1099186200000), CET)
|
||||
<< QDateTime::fromMSecsSinceEpoch(Q_INT64_C(1099182600000), CET)
|
||||
<< false << false;
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
void tst_QDateTime::operator_eqeq()
|
||||
|
|
|
|||
Loading…
Reference in New Issue