DRILL-870: C++ Client. Support negative interval types.

Project: http://git-wip-us.apache.org/repos/asf/incubator-drill/repo
Commit: http://git-wip-us.apache.org/repos/asf/incubator-drill/commit/632f5ca9
Tree: http://git-wip-us.apache.org/repos/asf/incubator-drill/tree/632f5ca9
Diff: http://git-wip-us.apache.org/repos/asf/incubator-drill/diff/632f5ca9

Branch: refs/heads/master
Commit: 632f5ca9cb8f096c1f70265ecd37d97aed17089e
Parents: b90956e
Author: Xiao Meng <[email protected]>
Authored: Fri May 30 13:12:46 2014 -0700
Committer: Jacques Nadeau <[email protected]>
Committed: Thu Jun 19 20:30:41 2014 -0700

----------------------------------------------------------------------
 .../native/client/src/clientlib/recordBatch.cpp | 60 ++++++++++++++------
 .../client/src/include/drill/recordBatch.hpp    | 26 ++++-----
 2 files changed, 55 insertions(+), 31 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/incubator-drill/blob/632f5ca9/contrib/native/client/src/clientlib/recordBatch.cpp
----------------------------------------------------------------------
diff --git a/contrib/native/client/src/clientlib/recordBatch.cpp 
b/contrib/native/client/src/clientlib/recordBatch.cpp
index 90fe11a..81b9dbe 100644
--- a/contrib/native/client/src/clientlib/recordBatch.cpp
+++ b/contrib/native/client/src/clientlib/recordBatch.cpp
@@ -20,10 +20,11 @@
 #include "drill/recordBatch.hpp"
 #include "utils.hpp"
 
-const uint32_t YEARS_TO_MONTHS=12;
-const uint32_t HOURS_TO_MILLIS=60*60*1000;
-const uint32_t MINUTES_TO_MILLIS=60*1000;
-const uint32_t SECONDS_TO_MILLIS=1000;
+const int32_t YEARS_TO_MONTHS=12;
+const int32_t DAYS_TO_MILLIS=24*60*60*1000;
+const int32_t HOURS_TO_MILLIS=60*60*1000;
+const int32_t MINUTES_TO_MILLIS=60*1000;
+const int32_t SECONDS_TO_MILLIS=1000;
 extern "C"
 {
     #include "y2038/time64.h"
@@ -476,45 +477,68 @@ std::string DateTimeTZHolder::toString(){
 std::string IntervalYearHolder::toString(){
     std::stringstream sstr;
 
-    uint32_t years  = (m_month / YEARS_TO_MONTHS);
-    uint32_t months = (m_month % YEARS_TO_MONTHS);
+    bool isNegative = (m_month < 0);
+    int32_t m = (isNegative ? - m_month : m_month);
 
+    int32_t years  = (m / YEARS_TO_MONTHS);
+    int32_t months = (m % YEARS_TO_MONTHS);
+
+    if (isNegative) sstr << "-"; // put negative sign here if negative
     sstr << years << "-" << months;
     return sstr.str();
 };
 
+// Drill may populate data like 25 hours ("0 25:0:0.0"), we should normalize 
it to
+// 1 day 1 hour "1 1:0:0.0"
 std::string IntervalDayHolder::toString(){
     std::stringstream sstr;
 
-    uint32_t hours  = m_ms / (HOURS_TO_MILLIS);
-    uint32_t millis     = m_ms % (HOURS_TO_MILLIS);
+    bool isNegative = (m_day < 0) || ( m_day == 0 && m_ms < 0);
+    int32_t days = (m_day < 0 ? - m_day : m_day);
+    int32_t ms = (m_ms < 0 ? - m_ms : m_ms);
+
+    days += ms / (DAYS_TO_MILLIS);
+    int32_t millis = ms % (DAYS_TO_MILLIS);
+    int32_t hours  = millis / (HOURS_TO_MILLIS);
+    millis = millis % (HOURS_TO_MILLIS);
 
-    uint32_t minutes = millis / (MINUTES_TO_MILLIS);
+    int32_t minutes = millis / (MINUTES_TO_MILLIS);
     millis      = millis % (MINUTES_TO_MILLIS);
 
-    uint32_t seconds = millis / (SECONDS_TO_MILLIS);
+    int32_t seconds = millis / (SECONDS_TO_MILLIS);
     millis      = millis % (SECONDS_TO_MILLIS);
 
-    sstr << m_day<< " " << hours << ":"<<minutes<<":"<<seconds<<"."<<millis;
+    assert(hours >=0 && hours <= 23);
+    if(isNegative) sstr << "-";
+    sstr << days << " " << hours << ":"<<minutes<<":"<<seconds<<"."<<millis;
     return sstr.str();
 };
 
 std::string IntervalHolder::toString(){
     std::stringstream sstr;
 
-    uint32_t years  = (m_month / YEARS_TO_MONTHS);
-    uint32_t months = (m_month % YEARS_TO_MONTHS);
+    bool isNegative = (m_month < 0) || (m_month == 0 && m_day < 0 ) || 
(m_month == 0 && m_day == 0 && m_ms < 0);
+    int32_t m = (m_month < 0 ? - m_month : m_month);
+    int32_t days = (m_day < 0 ? - m_day : m_day);
+    int32_t ms = (m_ms < 0 ? - m_ms : m_ms);
+
+    int32_t years  = (m / YEARS_TO_MONTHS);
+    int32_t months = (m % YEARS_TO_MONTHS);
 
-    uint32_t hours  = m_ms / (HOURS_TO_MILLIS);
-    uint32_t millis     = m_ms % (HOURS_TO_MILLIS);
+    days   += ms / (DAYS_TO_MILLIS);
+    int32_t millis = ms % (DAYS_TO_MILLIS);
+    int32_t hours  = millis / (HOURS_TO_MILLIS);
+    millis      = millis % (HOURS_TO_MILLIS);
 
-    uint32_t minutes = millis / (MINUTES_TO_MILLIS);
+    int32_t minutes = millis / (MINUTES_TO_MILLIS);
     millis      = millis % (MINUTES_TO_MILLIS);
 
-    uint32_t seconds = millis / (SECONDS_TO_MILLIS);
+    int32_t seconds = millis / (SECONDS_TO_MILLIS);
     millis      = millis % (SECONDS_TO_MILLIS);
 
-    sstr << years << "-" << months<< "-" << m_day<< " " << hours << 
":"<<minutes<<":"<<seconds<<"."<<millis;
+    assert(hours >=0 && hours <= 23);
+    if (isNegative) sstr << "-";
+    sstr << years << "-" << months<< "-" << days << " " << hours << 
":"<<minutes<<":"<<seconds<<"."<<millis;
     return sstr.str();
 };
 

http://git-wip-us.apache.org/repos/asf/incubator-drill/blob/632f5ca9/contrib/native/client/src/include/drill/recordBatch.hpp
----------------------------------------------------------------------
diff --git a/contrib/native/client/src/include/drill/recordBatch.hpp 
b/contrib/native/client/src/include/drill/recordBatch.hpp
index dab8b9b..984588f 100644
--- a/contrib/native/client/src/include/drill/recordBatch.hpp
+++ b/contrib/native/client/src/include/drill/recordBatch.hpp
@@ -454,41 +454,41 @@ struct DateTimeTZHolder: public DateTimeHolder{
 
 struct IntervalYearHolder{
     IntervalYearHolder(ByteBuf_t b){
-        m_month=*(uint32_t*)b;
+        m_month=*(int32_t*)b;
         load();
     }
     void load(){};
     std::string toString();
-    uint32_t m_month;
+    int32_t m_month;
     static uint32_t size(){ return sizeof(uint32_t); }
 };
 
 struct IntervalDayHolder{
     IntervalDayHolder(ByteBuf_t b){
-        m_day=*(uint32_t*)(b);
-        m_ms=*(uint32_t*)(b+sizeof(uint32_t));
+        m_day=*(int32_t*)(b);
+        m_ms=*(int32_t*)(b+sizeof(int32_t));
         load();
     }
     void load(){};
     std::string toString();
-    uint32_t m_day;
-    uint32_t m_ms;
+    int32_t m_day;
+    int32_t m_ms;
     static uint32_t size(){ return 2*sizeof(uint32_t)+4; }
 };
 
 struct IntervalHolder{
     IntervalHolder(ByteBuf_t b){
-        m_month=*(uint32_t*)b;
-        m_day=*(uint32_t*)(b+sizeof(uint32_t));
-        m_ms=*(uint32_t*)(b+2*sizeof(uint32_t));
+        m_month=*(int32_t*)b;
+        m_day=*(int32_t*)(b+sizeof(int32_t));
+        m_ms=*(int32_t*)(b+2*sizeof(int32_t));
         load();
     }
     void load(){};
     std::string toString();
-    uint32_t m_month;
-    uint32_t m_day;
-    uint32_t m_ms;
-    static uint32_t size(){ return 3*sizeof(uint32_t)+4; }
+    int32_t m_month;
+    int32_t m_day;
+    int32_t m_ms;
+    static uint32_t size(){ return 3*sizeof(int32_t)+4; }
 };
 
 /*

Reply via email to