From d58aadbce4b9f1e2ca145e63dde01883c6ca74cc Mon Sep 17 00:00:00 2001 From: Spiros Maggioros Date: Mon, 22 Jan 2024 00:35:19 +0200 Subject: [PATCH] updated some docstrings --- src/classes/list/doubly_linked_list.h | 2 +- src/classes/tree/avl_tree.h | 79 ++++-- src/classes/tree/bst.h | 87 +++++-- src/plotting/iterator/list_iterator.h | 45 ++++ src/plotting/iterator/list_link.h | 35 +++ .../graph_visual/graph_visualization.h | 244 ++++++++++-------- 6 files changed, 352 insertions(+), 140 deletions(-) diff --git a/src/classes/list/doubly_linked_list.h b/src/classes/list/doubly_linked_list.h index 5e9b268f..1096af5f 100644 --- a/src/classes/list/doubly_linked_list.h +++ b/src/classes/list/doubly_linked_list.h @@ -16,7 +16,7 @@ template class doubly_linked_list { bool empty() { return tail == nullptr; } - size_t size(){return __size;} + size_t size() { return __size; } doubly_list_iter begin() { return doubly_list_iter(root); } diff --git a/src/classes/tree/avl_tree.h b/src/classes/tree/avl_tree.h index ed2b99af..b25062ef 100644 --- a/src/classes/tree/avl_tree.h +++ b/src/classes/tree/avl_tree.h @@ -1,12 +1,20 @@ #ifdef __cplusplus +#include "../../visualization/tree_visual/tree_visualization.h" #include -#include #include -#include "../../visualization/tree_visual/tree_visualization.h" +#include #endif +/* + *Class for AVL tree. + */ template class avl_tree { public: + /* + *Contructor for AVL tree class. + *@param __elements: you can directly pass a vector so you don't have to do + *insert multiple times. + */ explicit avl_tree(std::vector __elements = {}) noexcept : root(nullptr) { if (!__elements.empty()) { for (T &x : __elements) { @@ -16,24 +24,42 @@ template class avl_tree { } ~avl_tree() noexcept {} + /* + *insert function. + *@param key: key to be inserted. + */ void insert(T key) { root = __insert(root, key); } + /* + *remove function. + *@param key: key to be removed. + */ void remove(T key) { root = __remove(root, key); } + /* + *inorder function. + *Returns vector, the elements inorder. + */ std::vector inorder() { std::vector path; __inorder([&](node *callbacked) { path.push_back(callbacked->info); }, root); return path; } - + /* + *preorder function. + *Returns vector, the elements preorder. + */ std::vector preorder() { std::vector path; __preorder([&](node *callbacked) { path.push_back(callbacked->info); }, root); return path; } - + /* + *postorder function. + *Returns vector, the elements postorder. + */ std::vector postorder() { std::vector path; __postorder([&](node *callbacked) { path.push_back(callbacked->info); }, @@ -41,12 +67,23 @@ template class avl_tree { return path; } - void visualize(){ + /* + *visualize function + *Returns .dot file that can be previewed using graphviz in vscode. + */ + void visualize() { std::string __generated = generate_visualization(); visualization::visualize(__generated); } private: + /* + *Struct for the node type pointer. + *@param info: the value of the node. + *@param height: height of each node. + *@param left: pointer to the left. + *@param right: pointer to the right. + */ typedef struct node { T info; int64_t height; @@ -54,6 +91,7 @@ template class avl_tree { struct node *right; } node; node *root; + int64_t height(node *root) { if (root == nullptr) return 0; @@ -167,32 +205,39 @@ template class avl_tree { } } - std::string generate_visualization(){ + std::string generate_visualization() { std::string __generate = __inorder_gen(root); return __generate; } - std::string __inorder_gen(node *root){ + std::string __inorder_gen(node *root) { std::string __s; - if(std::is_same_v || std::is_same_v){ - if(root -> left){ + if (std::is_same_v || std::is_same_v) { + if (root->left) { __s += root->info; - __s += "->"; + __s += "->"; __s += root->left->info; __s += "\n"; - __s += __inorder_gen(root->left); + __s += __inorder_gen(root->left); } - if(root -> right){ + if (root->right) { __s += root->info; - __s += "->"; + __s += "->"; __s += root->right->info; __s += "\n"; __s += __inorder_gen(root->right); } - } - else{ - if(root -> left){__s += std::to_string(root->info) + "->" + std::to_string(root->left->info) + "\n" + __inorder_gen(root->left);} - if(root -> right){__s += std::to_string(root->info) + "->" + std::to_string(root->right->info) + "\n" + __inorder_gen(root->right);} + } else { + if (root->left) { + __s += std::to_string(root->info) + "->" + + std::to_string(root->left->info) + "\n" + + __inorder_gen(root->left); + } + if (root->right) { + __s += std::to_string(root->info) + "->" + + std::to_string(root->right->info) + "\n" + + __inorder_gen(root->right); + } } return __s; } diff --git a/src/classes/tree/bst.h b/src/classes/tree/bst.h index a126aa72..72608c00 100644 --- a/src/classes/tree/bst.h +++ b/src/classes/tree/bst.h @@ -1,14 +1,22 @@ #ifdef __cplusplus +#include "../../visualization/tree_visual/tree_visualization.h" #include #include -#include #include #include -#include "../../visualization/tree_visual/tree_visualization.h" +#include #endif +/* + *Class for BST tree. + */ template class bst { public: + /* + *Contructor for BST tree class. + *@param __elements: you can directly pass a vector so you don't have to do + *insert multiple times. + */ explicit bst(std::vector __elements = {}) noexcept : root(nullptr) { if (!__elements.empty()) { for (T &x : __elements) { @@ -18,10 +26,22 @@ template class bst { } ~bst() noexcept {} + /* + *insert function. + *@param key: key to be inserted. + */ void insert(T key) { root = __insert(root, key); } + /* + *remove function. + *@param key: key to be removed. + */ void remove(T key) { root = __remove(root, key); } + /* + *level order function. + *Returns vector>, the level order of the Tree. + */ std::vector> level_order() { std::vector> levels; if (!root) { @@ -48,6 +68,10 @@ template class bst { return levels; } + /* + *inorder function. + *Returns vector, the elements inorder. + */ std::vector inorder() { std::vector path; __inorder([&](node *callbacked) { path.push_back(callbacked->info); }, @@ -55,6 +79,10 @@ template class bst { return path; } + /* + *preorder function. + *Returns vector, the elements preorder. + */ std::vector preorder() { std::vector path; __preorder([&](node *callbacked) { path.push_back(callbacked->info); }, @@ -62,6 +90,10 @@ template class bst { return path; } + /* + *postorder function. + *Returns vector, the elements postorder. + */ std::vector postorder() { std::vector path; __postorder([&](node *callbacked) { path.push_back(callbacked->info); }, @@ -69,17 +101,29 @@ template class bst { return path; } - void visualize(){ + /* + *visualize function + *Returns .dot file that can be previewed using graphviz in vscode. + */ + void visualize() { std::string __generated = generate_visualization(); visualization::visualize(__generated); } private: - struct node { + /* + *Struct for the node type pointer. + *@param info: the value of the node. + *@param left: pointer to the left. + *@param right: pointer to the right. + */ + typedef struct node { T info; - node *right, *left; - }; + node *right; + node *left; + } node; node *root; + node *new_node(T &key) { node *p = new node; p->info = key; @@ -157,32 +201,39 @@ template class bst { } } - std::string generate_visualization(){ + std::string generate_visualization() { std::string __generate = __inorder_gen(root); return __generate; } - std::string __inorder_gen(node *root){ + std::string __inorder_gen(node *root) { std::string __s; - if(std::is_same_v || std::is_same_v){ - if(root -> left){ + if (std::is_same_v || std::is_same_v) { + if (root->left) { __s += root->info; - __s += "->"; + __s += "->"; __s += root->left->info; __s += "\n"; - __s += __inorder_gen(root->left); + __s += __inorder_gen(root->left); } - if(root -> right){ + if (root->right) { __s += root->info; - __s += "->"; + __s += "->"; __s += root->right->info; __s += "\n"; __s += __inorder_gen(root->right); } - } - else{ - if(root -> left){__s += std::to_string(root->info) + "->" + std::to_string(root->left->info) + "\n" + __inorder_gen(root->left);} - if(root -> right){__s += std::to_string(root->info) + "->" + std::to_string(root->right->info) + "\n" + __inorder_gen(root->right);} + } else { + if (root->left) { + __s += std::to_string(root->info) + "->" + + std::to_string(root->left->info) + "\n" + + __inorder_gen(root->left); + } + if (root->right) { + __s += std::to_string(root->info) + "->" + + std::to_string(root->right->info) + "\n" + + __inorder_gen(root->right); + } } return __s; } diff --git a/src/plotting/iterator/list_iterator.h b/src/plotting/iterator/list_iterator.h index 9bdf852b..e93a8be2 100644 --- a/src/plotting/iterator/list_iterator.h +++ b/src/plotting/iterator/list_iterator.h @@ -2,10 +2,21 @@ #include "list_link.h" #endif +/* + *Iterator class for list + */ template class list_iter { public: list_iter() noexcept {} + /* + *copy constructor for list_iter class. + *@param node: the other list root. + */ list_iter(const std::shared_ptr<__link> node) noexcept : curr(node) {} + + /* + *operator ++ for list_iter class. + */ list_iter &operator++() { if (curr) { curr = curr->succ(); @@ -18,16 +29,32 @@ template class list_iter { return it; } + /* + *operator != for list_iter class. + */ bool operator!=(const list_iter &it) { return curr != it.curr; } + + /* + *operator * for list_iter class. + * i.e. list_iter it = l.begin(); + * *(it) -> gives the value of the first element. + */ T operator*() { return curr->val(); } private: std::shared_ptr<__link> curr; }; +/* + *Iterator for the class doubly_linked_list + */ template class doubly_list_iter { public: doubly_list_iter() noexcept {} + /* + *copy constructor for doubly_list_iter class. + *@param node: the other list root. + */ doubly_list_iter(const std::shared_ptr> node) noexcept : curr(node) {} doubly_list_iter &operator++() { @@ -36,11 +63,19 @@ template class doubly_list_iter { } return *this; } + + /* + *operator ++ for doubly_list_iter class. + */ doubly_list_iter operator++(int) { doubly_list_iter it = *this; ++*this; return it; } + + /* + *operator -- for doubly_list_iter class. + */ doubly_list_iter &operator--() { if (curr) { curr = curr->prev(); @@ -52,7 +87,17 @@ template class doubly_list_iter { --*this; return it; } + + /* + *operator != for list_iter class. + */ bool operator!=(const doubly_list_iter &it) { return curr != it.curr; } + + /* + *operator * for list_iter class. + * i.e. list_iter it = l.begin(); + * *(it) -> gives the value of the first element. + */ T operator*() { return curr->val(); } private: diff --git a/src/plotting/iterator/list_link.h b/src/plotting/iterator/list_link.h index d32b605f..9756ad06 100644 --- a/src/plotting/iterator/list_link.h +++ b/src/plotting/iterator/list_link.h @@ -2,18 +2,37 @@ #include #endif +/* + *Link for the list class. + */ template class __link { private: T pvalue; std::shared_ptr<__link> psucc; public: + /* + *contructor for __link class + *@param value: value assigned to the new __link type. + */ explicit __link(T value = 0) : pvalue(value), psucc(nullptr) {} + + /* + *val function. + *Returns the value of the __link type. + */ T val() { return pvalue; } + /* + *succ function. + *Returns the successor pointer of the __link type. + */ std::shared_ptr<__link> &succ() { return psucc; } }; +/* + *Link for the doubly_linked_list class. + */ template class doubly_link { private: T pvalue; @@ -21,11 +40,27 @@ template class doubly_link { std::shared_ptr pprev; public: + /* + *contructor for doubly_link class + *@param value: value assigned to the new doubly_link type. + */ explicit doubly_link(T value = 0) : pvalue(value), psucc(nullptr), pprev(nullptr) {} + /* + *val function. + *Returns the value of the doubly_link type. + */ T val() { return pvalue; } + /* + *succ function. + *Returns the successor pointer of the doubly_link type. + */ std::shared_ptr &succ() { return psucc; } + /* + *succ function. + *Returns the previous pointer of the doubly_link type. + */ std::shared_ptr &prev() { return pprev; } }; \ No newline at end of file diff --git a/src/visualization/graph_visual/graph_visualization.h b/src/visualization/graph_visual/graph_visualization.h index 3ddca1fb..ce7dd639 100644 --- a/src/visualization/graph_visual/graph_visualization.h +++ b/src/visualization/graph_visual/graph_visualization.h @@ -1,116 +1,152 @@ -#include -#include #include +#include +#include using namespace std; #define OPEN_COMMAND "open" // COLORS FOR TEXT -const char* reset = "\033[0m"; - const char* black = "\033[30m"; - const char* red = "\033[31m"; - const char* green = "\033[32m"; - const char* yellow = "\033[33m"; - const char* blue = "\033[34m"; - const char* magenta = "\033[35m"; - const char* cyan = "\033[36m"; - const char* white = "\033[37m"; - - const char* blackbackground = "\033[40m"; - const char* redbackground = "\033[41m"; - const char* greenbackground = "\033[42m"; - const char* yellowbackground = "\033[43m"; - const char* bluebackground = "\033[44m"; - const char* magentabackground = "\033[45m"; - const char* cyanbackground = "\033[46m"; - const char* whitebackground = "\033[47m"; - - const char* bold = "\033[1m"; - const char* underline = "\033[4m"; - const char* blink = "\033[5m"; - const char* inverse = "\033[7m"; - - -namespace graph_visualization{ - - void visualize(std::string &__generate, std::string newFileName = "unnamed.dot") { - auto start_time = std::chrono::high_resolution_clock::now(); - try { - if (newFileName.size() < 5 || newFileName.substr(newFileName.length() - 4) != ".dot") newFileName += ".dot"; - //newFileName = "examples/" + newFileName; - // Open the file for writing - std::ofstream outFile(newFileName); - - // Check if the file is successfully opened - if (outFile.is_open()) { - // Write the DOT format header - outFile << "graph G{" << std::endl; - - // Generate DOT code recursively - outFile << __generate; - // Write the DOT format footer - outFile << "}" << std::endl; - - // Close the file - outFile.close(); - - std::cout << green << "Visualization file '" << newFileName << "' created successfully." << std::endl << reset; - auto end_time = std::chrono::high_resolution_clock::now(); - auto duration = std::chrono::duration_cast(end_time - start_time); - double runtime_sec = static_cast(duration.count()) / 1e6; - - std::cout << blue << "Visualization runtime: " << runtime_sec << " sec" << std::endl << reset; - std::string openCommand = OPEN_COMMAND + std::string(" ") + newFileName; - system(openCommand.c_str()); - } else { - std::cerr << red << "Error: Unable to open file '" << newFileName << "' for writing." << std::endl << reset; - } - } catch (const std::exception& e) { - std::cerr << red << "Error: " << e.what() << std::endl << reset; +const char *reset = "\033[0m"; +const char *black = "\033[30m"; +const char *red = "\033[31m"; +const char *green = "\033[32m"; +const char *yellow = "\033[33m"; +const char *blue = "\033[34m"; +const char *magenta = "\033[35m"; +const char *cyan = "\033[36m"; +const char *white = "\033[37m"; + +const char *blackbackground = "\033[40m"; +const char *redbackground = "\033[41m"; +const char *greenbackground = "\033[42m"; +const char *yellowbackground = "\033[43m"; +const char *bluebackground = "\033[44m"; +const char *magentabackground = "\033[45m"; +const char *cyanbackground = "\033[46m"; +const char *whitebackground = "\033[47m"; + +const char *bold = "\033[1m"; +const char *underline = "\033[4m"; +const char *blink = "\033[5m"; +const char *inverse = "\033[7m"; + +/* + *namespace for graph visualization function and .dot files creation. + */ +namespace graph_visualization { +/* + *visualize function. + *@param __generate: string that contains the needed data to generate the .dot + *file. + *@param newFileName: if needed, the filename can be changed(default + *"unnamed.dot") + */ +void visualize(std::string &__generate, + std::string newFileName = "unnamed.dot") { + auto start_time = std::chrono::high_resolution_clock::now(); + try { + if (newFileName.size() < 5 || + newFileName.substr(newFileName.length() - 4) != ".dot") + newFileName += ".dot"; + // newFileName = "examples/" + newFileName; + // Open the file for writing + std::ofstream outFile(newFileName); + + // Check if the file is successfully opened + if (outFile.is_open()) { + // Write the DOT format header + outFile << "graph G{" << std::endl; + + // Generate DOT code recursively + outFile << __generate; + // Write the DOT format footer + outFile << "}" << std::endl; + + // Close the file + outFile.close(); + + std::cout << green << "Visualization file '" << newFileName + << "' created successfully." << std::endl + << reset; + auto end_time = std::chrono::high_resolution_clock::now(); + auto duration = std::chrono::duration_cast( + end_time - start_time); + double runtime_sec = static_cast(duration.count()) / 1e6; + + std::cout << blue << "Visualization runtime: " << runtime_sec << " sec" + << std::endl + << reset; + std::string openCommand = OPEN_COMMAND + std::string(" ") + newFileName; + system(openCommand.c_str()); + } else { + std::cerr << red << "Error: Unable to open file '" << newFileName + << "' for writing." << std::endl + << reset; } - }; - + } catch (const std::exception &e) { + std::cerr << red << "Error: " << e.what() << std::endl << reset; + } }; - -namespace digraph_visualization{ - - void visualize(std::string &__generate, std::string newFileName = "unnamed.dot") { - auto start_time = std::chrono::high_resolution_clock::now(); - try { - if (newFileName.size() < 5 || newFileName.substr(newFileName.length() - 4) != ".dot") newFileName += ".dot"; - //newFileName = "examples/" + newFileName; - // Open the file for writing - std::ofstream outFile(newFileName); - - // Check if the file is successfully opened - if (outFile.is_open()) { - // Write the DOT format header - outFile << "digraph G{" << std::endl; - - // Generate DOT code recursively - outFile << __generate; - // Write the DOT format footer - outFile << "}" << std::endl; - - // Close the file - outFile.close(); - - std::cout << green << "Visualization file '" << newFileName << "' created successfully." << std::endl << reset; - auto end_time = std::chrono::high_resolution_clock::now(); - auto duration = std::chrono::duration_cast(end_time - start_time); - double runtime_sec = static_cast(duration.count()) / 1e6; - - std::cout << blue << "Visualization runtime: " << runtime_sec << " sec" << std::endl << reset; - std::string openCommand = OPEN_COMMAND + std::string(" ") + newFileName; - system(openCommand.c_str()); - } else { - std::cerr << red << "Error: Unable to open file '" << newFileName << "' for writing." << std::endl << reset; - } - } catch (const std::exception& e) { - std::cerr << red << "Error: " << e.what() << std::endl << reset; +}; // namespace graph_visualization + +/* + *namespace for di-graph visualization function and .dot files creation. + */ +namespace digraph_visualization { +/* + *visualize function. + *@param __generate: string that contains the needed data to generate the .dot + *file. + *@param newFileName: if needed, the filename can be changed(default + *"unnamed.dot") + */ +void visualize(std::string &__generate, + std::string newFileName = "unnamed.dot") { + auto start_time = std::chrono::high_resolution_clock::now(); + try { + if (newFileName.size() < 5 || + newFileName.substr(newFileName.length() - 4) != ".dot") + newFileName += ".dot"; + // newFileName = "examples/" + newFileName; + // Open the file for writing + std::ofstream outFile(newFileName); + + // Check if the file is successfully opened + if (outFile.is_open()) { + // Write the DOT format header + outFile << "digraph G{" << std::endl; + + // Generate DOT code recursively + outFile << __generate; + // Write the DOT format footer + outFile << "}" << std::endl; + + // Close the file + outFile.close(); + + std::cout << green << "Visualization file '" << newFileName + << "' created successfully." << std::endl + << reset; + auto end_time = std::chrono::high_resolution_clock::now(); + auto duration = std::chrono::duration_cast( + end_time - start_time); + double runtime_sec = static_cast(duration.count()) / 1e6; + + std::cout << blue << "Visualization runtime: " << runtime_sec << " sec" + << std::endl + << reset; + std::string openCommand = OPEN_COMMAND + std::string(" ") + newFileName; + system(openCommand.c_str()); + } else { + std::cerr << red << "Error: Unable to open file '" << newFileName + << "' for writing." << std::endl + << reset; } - }; - + } catch (const std::exception &e) { + std::cerr << red << "Error: " << e.what() << std::endl << reset; + } }; + +}; // namespace digraph_visualization