From a8a525df81403f23042b113befd321d93afaf02d Mon Sep 17 00:00:00 2001 From: unknown Date: Wed, 23 Sep 2020 17:55:54 +0700 Subject: [PATCH] [3sem] dsaa02 mod protecc and general fix --- 3sem/data structures and algos/02/program.cpp | 102 +++++++++++++----- 1 file changed, 75 insertions(+), 27 deletions(-) diff --git a/3sem/data structures and algos/02/program.cpp b/3sem/data structures and algos/02/program.cpp index 1f2a704..3e106d0 100644 --- a/3sem/data structures and algos/02/program.cpp +++ b/3sem/data structures and algos/02/program.cpp @@ -6,6 +6,7 @@ #include #include #include +#include #ifdef DEBUG #define printf_d printf @@ -20,12 +21,10 @@ private: int _capacity; void _resize(int new_size) { - int *new_container = new int [new_size]; - for (int i = 0; i < this->_size; i++) { - *(new_container + i) = *(this->container + i); - } - std::swap(this->container, new_container); - delete [] new_container; + int *new_container = new int [new_size]{0}; + std::copy(this->container, this->container + this->size(), new_container); + delete [] this->container; + this->container = new_container; this->_capacity = new_size; } @@ -35,9 +34,7 @@ public: this->container = new int [this->_capacity]{0}; } ~DynIntArr() { - if (this->container != nullptr) { - delete [] this->container; - } + delete [] this->container; } int &at(int pos) { @@ -54,6 +51,20 @@ public: this->at(this->_size++) = val; } + void insert(int pos, int val) { + if (pos < 0 || pos > this->_capacity) { + throw std::runtime_error("Illegal array access"); + } + if (this->_size+1 > this->_capacity) { + this->_resize(this->_capacity*2); + } + for (int i = this->size(); i > pos; i--) { + this->at(i) = this->at(i-1); + } + this->at(pos) = val; + this->_size += 1; + } + int size() const { // NOLINT(modernize-use-nodiscard) return this->_size; } @@ -72,27 +83,31 @@ inline void time_passed(std::chrono::system_clock::time_point start, double &hol void algo_01(DynIntArr &cont); // algo with my container void algo_02(std::vector &cont); // algo with stl's vector +void algo_03(std::list &cont); // algo with stl's list // let's assume we are not including reading of data into algo's time // 'cause it can at worst be O(inf) int main() { int reserve = 50; - DynIntArr dyn_arr(reserve); + std::list lst_int; std::vector vec_int; vec_int.reserve(reserve); + DynIntArr dyn_arr(reserve); int N = 0; std::cout << "N="; std::cin >> N; + auto lit = lst_int.begin(); for (int i = 0; i < N; i++) { int num = 0; std::cin >> num; dyn_arr.add(num); vec_int.push_back(num); + lst_int.push_back(num); } - double fft, sft = fft = 0; + double fft, sft, tft = sft = fft = 0; if (N <= 2) { // Well, even if smth. is missed there is no way to determine goto endo; @@ -108,10 +123,18 @@ int main() { algo_02(vec_int); time_passed(start, sft); } + { // algo with stl's list + auto start = std::chrono::high_resolution_clock::now(); + algo_03(lst_int); + time_passed(start, tft); + } { // let's check integrity of content assert(dyn_arr.size() == vec_int.size()); + assert(dyn_arr.size() == lst_int.size()); + auto lit = lst_int.begin(); for (int i = 0; i < dyn_arr.size(); i++) { assert(dyn_arr.at(i) == vec_int.at(i)); + assert(dyn_arr.at(i) == *(lit++)); } } @@ -124,19 +147,24 @@ int main() { std::cout << std::endl; printf( - "algo_01 is %s than algo_02 by %.0f microseconds", + "algo_01 is %s than algo_02 by %.0f microseconds\n", (fft > sft? "slower" : "faster"), fabs(fft - sft) ); + printf( + "algo_01 is %s than algo_03 by %.0f microseconds\n", + (fft > tft? "slower" : "faster"), fabs(fft - tft) + ); + return 0; } void algo_01(DynIntArr &cont) { - if (cont.size() <= 2) { // See this_file:97 + if (cont.size() <= 2) { // See this_file:112 return; } - int step = (cont.at(cont.size()-1) - cont.at(0)) / (cont.size() - 1); + int step = (cont.at(cont.size()-1) - cont.at(0)) / (cont.size()); int miss_pos = -1; for (int i = 1; i < cont.size(); i++) { int p = cont.at(i - 1), @@ -149,21 +177,17 @@ void algo_01(DynIntArr &cont) { } if (miss_pos != -1) { - int val = cont.at(0) - step; - int elc = cont.size() + 1; - cont = DynIntArr(cont.size() + 1); - for (int i = 0; i < elc; i++) { - cont.add(val += step); - } + int val = cont.at(miss_pos) - step; + cont.insert(miss_pos, val); } } void algo_02(std::vector &cont) { - if (cont.size() <= 2) { // See this_file:97 + if (cont.size() <= 2) { // See this_file:112 return; } - int step = (cont.at(cont.size()-1) - cont.at(0)) / (cont.size() - 1); + int step = (cont.at(cont.size()-1) - cont.at(0)) / (cont.size()); int miss_pos = -1; for (int i = 1; i < cont.size(); i++) { int p = cont.at(i - 1), @@ -176,13 +200,37 @@ void algo_02(std::vector &cont) { } if (miss_pos != -1) { - int val = cont.at(0) - step; - int elc = cont.size() + 1; - cont.clear(); - for (int i = 0; i < elc; i++) { - cont.push_back(val += step); + auto vit = cont.begin(); + std::advance(vit, miss_pos); + cont.insert(vit, *vit - step); + } +} + +void algo_03(std::list &cont) { + if (cont.size() <= 2) { // See this_file:112 + return; + } + + int step = (cont.back() - cont.front()) / (cont.size()); + int miss_pos = -1; + { + auto lit = cont.begin(); + for (int i = 1; i < cont.size(); i++) { + int p = *lit++, + c = *(lit); + + if (c - p != step) { + miss_pos = i; + break; + } } } + + if (miss_pos != -1) { + auto lit = cont.begin(); + std::advance(lit, miss_pos); + cont.insert(lit, *lit - step); + } }