]> pilppa.org Git - lib1wire.git/commitdiff
Several data read and store fixes.
authorMika Laitio <lamikr@pilppa.org>
Mon, 27 Dec 2010 16:47:03 +0000 (18:47 +0200)
committerMika Laitio <lamikr@pilppa.org>
Mon, 27 Dec 2010 16:47:03 +0000 (18:47 +0200)
Fix for "month" number in month folder and file-names when storing data.
Fixes for reading data, when the file containing data can not be opened.
Memory leak fixes.
Hourly data read fixes.

Signed-off-by: Mika Laitio <lamikr@pilppa.org>
src/Data.cc
src/Data.hh
src/Date.cc
src/Date.hh
src/DeviceConfig.cc
src/DeviceData.cc
src/DeviceData.hh
src/W1Store.cc
src/W1Store.hh
src_test/test_w1_datalog_read.cc

index 29325b73d0d6fdaa077ba227e0c2b58eb7326bf7..c964bc411f3f2d8763aeec3a135763a69b8d2d22 100644 (file)
@@ -62,7 +62,6 @@ Data::Data(std::valarray<double> value_arr_param, Date *date_param) {
        unsigned int ii;
 
        value_arr.resize(value_arr_param.size());
-
        for (ii = 0; ii < value_arr_param.size(); ii++) {
                value_arr[ii]   = value_arr_param[ii];
        }
@@ -72,6 +71,13 @@ Data::Data(std::valarray<double> value_arr_param, Date *date_param) {
 Data::~Data() {
 }
 
+Data *Data::clone() {
+       Data    *ret_val;
+
+       ret_val = new Data(value_arr, &date_time);
+       return ret_val;
+}
+
 plp::Date Data::get_date() {
        return date_time;
 }
@@ -207,3 +213,18 @@ Data *DataRange::get_first_data() {
 Data *DataRange::get_last_data() {
        return get_data(row_count - 1);
 }
+
+void DataRange::printout() {
+       int     ii;
+       Data    *data;
+
+       log_debug("---- DataRange, number of data items: %d\n ----", row_count);
+       for (ii = 0; ii < row_count; ii++) {
+               data    = get_data(ii);
+               if (data != NULL) {
+                       data->printout();
+                       delete(data);
+               }
+       }
+       log_debug("---- DataRange printout done ----\n");
+}
index 35af7c615f64ed8df1415fe76c92656cc0d416e1..8a8a28a831dc6ff13dc945a1daf63f10d424f302 100644 (file)
@@ -22,6 +22,7 @@ namespace w1 {
                        Data(std::vector<double> vector_param, plp::Date *date_param);
                        Data(std::valarray<double> value_arr_param, plp::Date *date_param);
                        virtual ~Data();
+                       Data *clone();
                        plp::Date get_date();
                        void set_date(plp::Date date);
                        void printout();
@@ -42,6 +43,7 @@ namespace w1 {
                        Data *get_last_data();
                        int get_data_row_count();
                        int get_data_column_count();
+                       void printout();
                protected:
                        double                          *val_matrix;
                        std::vector<plp::Date *>        date_list;
index 8c03c5bd661e6ed7a5c371037ef4e0923b268af2..e82ee999edc8dad3c321c7de7cda3d54558ec974 100644 (file)
@@ -27,7 +27,7 @@ Date::Date() {
        time(&wtime);
        ltime   = localtime(&wtime);
        year    = 1900 + ltime->tm_year;
-       month   = ltime->tm_mon;
+       month   = ltime->tm_mon + 1;    // ltime-month: values 0 - 11...
        day     = ltime->tm_mday;
        hour    = ltime->tm_hour;
        min     = ltime->tm_min;
@@ -137,6 +137,60 @@ void Date::tomorrow() {
        }
 }
 
+void Date::next_hour() {
+       if ((hour >= 0) &&
+           (hour <= 24)) {
+               hour++;
+               if (hour > 24) {
+                       hour    = 0;
+                       tomorrow();
+               }
+       }
+}
+
+void Date::inc_minutes(int minutes) {
+       int     day_c;
+       int     hour_c;
+       int     ii;
+
+       day_c   = minutes / 1440;
+       minutes = minutes - day_c * 1440;
+       hour_c  = minutes / 60;
+       minutes = minutes - hour_c * 60;
+       for (ii = 0; ii < day_c; ii++) {
+               tomorrow();
+       }
+       for (ii = 0; ii < hour_c; ii++) {
+               hour++;
+               if (hour > 24) {
+                       hour    = 0;
+                       tomorrow();
+               }
+       }
+       min     = min + minutes;
+       if (min >= 60) {
+               min     = min % 60;
+               hour++;
+               if (hour > 24) {
+                       hour    = 0;
+                       tomorrow();
+               }
+       }
+}
+
+void Date::inc_seconds(int seconds) {
+       int     min_c;
+
+       min_c   = seconds / 60;
+       seconds = seconds - min_c * 60;
+       inc_minutes(min_c);
+       sec     = sec + seconds;
+       if (sec >= 60) {
+               sec     = sec % 60;
+               inc_minutes(1);
+       }
+}
+
 string Date::to_string() {
        char    buffer[30];
        string  ret_val;
index b2b908d38fbe2532b6b6e45dda778ea8e6ae95c7..2d6fd757723a92d200b61a124383e0e04ba6fc7a 100644 (file)
@@ -24,6 +24,9 @@ namespace plp {
                        void printout();
                        bool is_leap_year();
                        void tomorrow();
+                       void next_hour();
+                       void inc_minutes(int minutes);
+                       void inc_seconds(int seconds);
                        Date *clone();
                        void copy(Date *date);
                        bool before(Date date2);
index f9e8f72684747cee8057c848ca8a42b6f3ec7867..19cfbb9ab7c848cd3188faf8e3d40d86c1f4a037 100644 (file)
@@ -128,7 +128,7 @@ enum_summary_calculation DeviceConfig::get_summary_calculation_type() {
 
        ret_val = MEAN;
        if (device_type.empty() == false) {
-               if (device_type.compare("counter") == 0) {
+               if (device_type.compare("Counter Device") == 0) {
                        ret_val = DELTA;
                }
        }
index 259d821ae38310cebc583baeab048c4e637af82c..13c28aa22f63207e323f26eb2dfd2532f87ed787 100644 (file)
@@ -169,59 +169,137 @@ long int get_interval_type(Date *start_date,
        return ret_val;
 }
 
-Data *DeviceData::get_daily_summary(Date *date) {
+Data *DeviceData::get_day_summary(Date *date) {
        Data    *ret_val;
        W1Store *store;
+       bool    suc_flg;
+
+       ret_val = NULL;
+       store   = new W1Store(device_id, date);
+       if (store != NULL) {
+               suc_flg = store->load();
+               if (suc_flg == true) {
+                       switch(summary_calc_type) {
+                               case SUM:
+                                       ret_val = store->get_sum();
+                                       break;
+                               case DELTA:
+                                       ret_val = store->get_delta();
+                                       break;
+                               case MEAN:
+                               default:
+                                       ret_val = store->get_mean();
+                                       break;
+                               case MAX:
+                                       ret_val = store->get_max();
+                                       break;
+                               case MIN:
+                                       ret_val = store->get_min();
+                                       break;
+                       }
+                       if (ret_val != NULL) {
+                               ret_val->printout();
+                       }
+                       else {
+                               log_error("Could not read data log for device: %s\n", device_id.c_str());
+                       }
+               }
+               else {
+                       log_error("Could not read data log for device: %s. Data file open load failed.\n", device_id.c_str());
+               }
+       }
+       else {
+               log_error("Could not read data log for device: %s\n", device_id.c_str());
+       }
+       delete(store);
+       return ret_val;
+}
+
+DataRange *DeviceData::get_daily_summary(Date *start_date,
+                                       Date *end_date) {
+       DataRange       *ret_val;
+       Data            *data;
+       Date            *date;
+
+       ret_val = NULL;
+       date    = start_date->clone();
+       while(date->before(*end_date)) {
+               data    = get_day_summary(date);
+               if (data != NULL) {
+                       if (ret_val == NULL) {
+                               ret_val = new DataRange(*data);
+                       }
+                       else {
+                               ret_val->add_data(*data);
+                       }
+                       delete(data);
+               }
+               date->tomorrow();
+       }
+       delete(date);
+       return ret_val;
+}
+
+vector<Data *> DeviceData::get_hourly_summary(Date *date) {
+       vector<Data *>  ret_val;
+       W1Store *       store;
 
        store   = new W1Store(device_id, date);
        store->load();
        switch(summary_calc_type) {
+/*
                case SUM:
                        ret_val = store->get_sum();
                        break;
+*/
                case DELTA:
-                       ret_val = store->get_delta();
+                       ret_val = store->get_delta(3600);
                        break;
                case MEAN:
                default:
-                       ret_val = store->get_mean();
+                       ret_val = store->get_mean(3600);
                        break;
+/*
                case MAX:
                        ret_val = store->get_max();
                        break;
                case MIN:
                        ret_val = store->get_min();
                        break;
+*/
        }
-       ret_val->printout();
        delete(store);
-
        return ret_val;
 }
 
-DataRange *DeviceData::get_daily_summary(Date *start_date,
+DataRange *DeviceData::get_hourly_summary(Date *start_date,
                                        Date *end_date) {
        DataRange       *ret_val;
+       vector<Data *>  dta_list;
        Data            *data;
        Date            *date;
 
        ret_val = NULL;
        date    = start_date->clone();
        while(date->before(*end_date)) {
-               data    = get_daily_summary(date);
-               if (ret_val == NULL) {
-                       ret_val = new DataRange(*data);
-               }
-               else {
-                       ret_val->add_data(*data);
+               dta_list        = get_hourly_summary(date);
+               for(vector<Data *>::iterator list_iter = dta_list.begin(); list_iter != dta_list.end(); list_iter++) {
+                       data    = (Data *)*list_iter;
+                       if (data != NULL) {
+                               if (ret_val == NULL) {
+                                       ret_val = new DataRange(*data);
+                               }
+                               else {
+                                       ret_val->add_data(*data);
+                               }
+                               delete(data);
+                       }
                }
-               delete(data);
                date->tomorrow();
        }
        delete(date);
        return ret_val;
 }
-
 DataRange *DeviceData::get_data(Date *start_date,
                                Date *end_date) {
        DataRange       *ret_val;
@@ -237,6 +315,7 @@ DataRange *DeviceData::get_data(Date *start_date,
                        break;
                case 1:
                        log_debug("get monthly summary\n");
+                       ret_val = get_daily_summary(start_date, end_date);
                        break;
                case 2:
                        log_debug("get daily summary\n");
@@ -244,6 +323,7 @@ DataRange *DeviceData::get_data(Date *start_date,
                        break;
                case 3:
                        log_debug("get hourly summary\n");
+                       ret_val = get_hourly_summary(start_date, end_date);
                        break;
                case 4:
                        log_debug("get minute summary data\n");
index 33629714972c978b5ff3695430bdad3b7eb6bc56..a4c06ac8ef5d3eb8c98caa23f8a7d0aabc66d466 100644 (file)
@@ -27,8 +27,10 @@ namespace w1 {
                         * Get summary data calculated from the daily data items that is meaning full.
                         * Depending from the device type, it may be daily mean value, daily delta, highest value, etc...
                         */
-                       Data *get_daily_summary(plp::Date *date);
+                       Data *get_day_summary(plp::Date *date);
                        DataRange *get_daily_summary(plp::Date *start_date, plp::Date *end_date);
+                       std::vector<Data *> get_hourly_summary(plp::Date *date);
+                       DataRange *get_hourly_summary(plp::Date *start_date, plp::Date *end_date);
                        DataRange *get_data(plp::Date *start_date, plp::Date *end_date);
                protected:
                        std::string                     device_id;
index 8debaa1b316f336e33a5265edcbebf5e09fe4ef7..9913d0dcd8cefad6787cdcf299accf15fd56b210 100644 (file)
@@ -109,11 +109,13 @@ void W1Store::store(std::string device_id,
        delete(date);
 }
 
-void W1Store::load() {
+bool W1Store::load() {
        Data            *data;
        ifstream        in;
        string          line;
+       bool            ret_val;
 
+       ret_val = false;
        if (store_data != NULL) {
                delete(store_data);
                store_data      = NULL;
@@ -131,7 +133,12 @@ void W1Store::load() {
                        }
                        delete(data);
                }
+               ret_val = true;
        }
+       else {
+               log_error("Could not load data from file: %s\n", store_file_name.c_str());
+       }
+       return ret_val;
 }
 
 Data *W1Store::get_sum() {
@@ -330,6 +337,165 @@ Data *W1Store::get_min() {
        return ret_val;
 }
 
+vector<Data *> W1Store::get_mean(int freq_sec) {
+       int             row_count;
+       int             col_count;
+       int             d_count;
+       int             jj;
+       int             ii;
+       Data            *data;
+       Data            *calc;
+       Date            *limit_d;
+       Date            date;
+       vector<Data *>  ret_val;
+
+       calc    = NULL;
+       limit_d = NULL;
+       d_count = 1;
+       if (store_data == NULL) {
+               load();
+       }
+       if (store_data != NULL) {
+               row_count       = store_data->get_data_row_count();
+               if (row_count > 0) {
+                       col_count       = store_data->get_data_column_count();
+                       if (col_count > 0) {
+                               for (ii = 0; ii < row_count; ii++) {
+                                       data    = store_data->get_data(ii);
+                                       if (data != NULL) {
+                                               if (calc == NULL) {
+                                                       d_count         = 1;
+                                                       calc            = data->clone();
+                                                       limit_d         = data->get_date().clone();
+                                                       limit_d->min    = 0;
+                                                       limit_d->sec    = 0;
+                                                       limit_d->inc_seconds(freq_sec);
+                                               }
+                                               else {
+                                                       date    = data->get_date();
+                                                       if (date.before(*limit_d)) {
+                                                               for (jj = 0; jj < col_count; jj++) {
+                                                                       calc->value_arr[jj]     = calc->value_arr[jj] + data->value_arr[jj];
+                                                               }
+                                                               d_count++;
+                                                       }
+                                                       else {
+                                                               for (jj = 0; jj < col_count; jj++) {
+                                                                       calc->value_arr[jj]     = calc->value_arr[jj] / d_count;
+                                                               }
+                                                               ret_val.push_back(calc);
+                                                               d_count         = 1;
+                                                               calc            = data->clone();
+                                                               if (limit_d != NULL) {
+                                                                       delete(limit_d);
+                                                               }
+                                                               limit_d         = data->get_date().clone();
+                                                               limit_d->min    = 0;
+                                                               limit_d->sec    = 0;
+                                                               limit_d->inc_seconds(freq_sec);
+                                                       }
+                                               }
+                                               delete(data);
+                                       }
+                               }
+                               if (calc != NULL) {
+                                       delete(calc);
+                                       calc    = NULL;
+                               }
+                               if (limit_d != NULL) {
+                                       delete(limit_d);
+                               }
+                       }
+               }
+       }
+       return ret_val;
+}
+
+vector<Data *> W1Store::get_delta(int freq_sec) {
+       int             row_count;
+       int             col_count;
+       int             jj;
+       int             ii;
+       Data            *data;
+       Data            *calc1;
+       Data            *calc2;
+       Date            *limit_d;
+       Date            date;
+       vector<Data *>  ret_val;
+
+       calc1   = NULL;
+       calc2   = NULL;
+       limit_d = NULL;
+       if (store_data == NULL) {
+               load();
+       }
+       if (store_data != NULL) {
+               row_count       = store_data->get_data_row_count();
+               if (row_count > 0) {
+                       col_count       = store_data->get_data_column_count();
+                       if (col_count > 0) {
+                               for (ii = 0; ii < row_count; ii++) {
+                                       data    = store_data->get_data(ii);
+                                       if (data != NULL) {
+                                               if (calc1 == NULL) {
+                                                       calc1           = data->clone();
+                                                       limit_d         = data->get_date().clone();
+                                                       limit_d->min    = 0;
+                                                       limit_d->sec    = 0;
+                                                       limit_d->inc_seconds(freq_sec);
+                                                       if (calc2 != NULL) {
+                                                               delete(calc2);
+                                                       }
+                                                       calc2           = NULL;
+                                               }
+                                               else {
+                                                       date    = data->get_date();
+                                                       if (date.before(*limit_d)) {
+                                                               if (calc2 != NULL) {
+                                                                       delete(calc2);
+                                                               }
+                                                               calc2   = data->clone();
+                                                       }
+                                                       else {
+                                                               if (calc2 == NULL) {
+                                                                       calc2   = calc1->clone();
+                                                               }
+                                                               for (jj = 0; jj < col_count; jj++) {
+                                                                       calc2->value_arr[jj]    = calc2->value_arr[jj] - calc1->value_arr[jj];
+                                                               }
+                                                               ret_val.push_back(calc2);
+                                                               delete(calc1);
+                                                               calc1   = data->clone();
+                                                               calc2   = NULL; // do not delete calc2 as it's stored to array
+                                                               if (limit_d != NULL) {
+                                                                       delete(limit_d);
+                                                               }
+                                                               limit_d         = data->get_date().clone();
+                                                               limit_d->min    = 0;
+                                                               limit_d->sec    = 0;
+                                                               limit_d->inc_seconds(freq_sec);
+                                                       }
+                                               }
+                                               delete(data);
+                                       }
+                               }
+                               if (calc1 != NULL) {
+                                       delete(calc1);
+                                       calc1   = NULL;
+                               }
+                               if (calc2 != NULL) {
+                                       delete(calc2);
+                                       calc2   = NULL;
+                               }
+                               if (limit_d != NULL) {
+                                       delete(limit_d);
+                               }
+                       }
+               }
+       }
+       return ret_val;
+}
+
 DataRange *W1Store::get_oldest_and_newest_data() {
        DataRange       *ret_val;
        ifstream        in;
index 53b124aa0654a7dcefa18ee4a8f10b3559dc160f..fb6fadbdae4278b2312b40fcc4adb4269c7dc184 100644 (file)
@@ -10,6 +10,9 @@
 
 #include <string>
 #include <list>
+#include <vector>
+
+#include <stdbool.h>
 
 #include "Data.hh"
 #include "Date.hh"
@@ -24,12 +27,14 @@ namespace w1 {
                        static std::string get_dir_name(std::string device_id, plp::Date *ltime);
                        static std::string get_file_name(std::string device_id, plp::Date *ltime);
                        static void store(std::string device_id, std::list<std::string> *string_list);
-                       void load();
+                       bool load();
                        Data *get_sum();
                        Data *get_delta();
                        Data *get_mean();
                        Data *get_max();
                        Data *get_min();
+                       std::vector<w1::Data *> get_mean(int freq_sec);
+                       std::vector<w1::Data *> get_delta(int freq_sec);
                        w1::Data *get_oldest_data();
                        w1::Data *get_newest_data();
                        w1::DataRange *get_oldest_and_newest_data();
index 046a47508c98eb52753636223a1498d9935bbb25..d135c03f611b856f9fa26ecbf927a7d414433ceb 100644 (file)
@@ -82,10 +82,11 @@ int main(int argc, char** argv) {
                                                d1      = fdata->get_date();
                                                d2      = ldata->get_date();
                                                dr2     = dta->get_data(&d1, &d2);
-                                               delete(ldata);
                                                if (dr2 != NULL) {
+                                                       dr2->printout();
                                                        delete(dr2);
                                                }
+                                               delete(ldata);
                                        }
                                        delete(fdata);
                                }