-
Notifications
You must be signed in to change notification settings - Fork 8
Смирнов Илья #2
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
Смирнов Илья #2
Conversation
|
@KorotinEgor, @kermanglobe, хоть с CMake и проблемы, но сам код можете проверять |
kermanglobe
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
если мне не изменяет память, то должна ещё быть упорядоченная таблица на массиве
include/AVLTreeTable.h
Outdated
| std::vector<Node*> memorysearch(std::string name); | ||
| int balance(Node* nd); | ||
| void smallleftrot(Node* xparent, Node* x); | ||
| void smallrightrot(Node* xparent, Node* x); | ||
| void bigleftrot(Node* xparent, Node* x); | ||
| void bigrightrot(Node* xparent, Node* x); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
я бы эти методы в private поместил
| void clear(std::string name); | ||
| polynoms Arithmetic(std::string strexpr); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
в чём резон помещать метод для вычисления выражений внутрь таблиц?
include/AVLTreeTable.h
Outdated
| ~AVLTreeTable(); | ||
| polynoms search(std::string name); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
ключ-строку нужно передавать как const std::string& (иначе каждый раз при вызове функции будет происходить копирование)
| } | ||
| polynoms entered(entmon); | ||
| table.add(name, entered); | ||
| cout << "UnorderedTable: add. Operations: " << counttable << endl; | ||
| tree.add(name, entered); | ||
| cout << "AVLTreeTable: add. Operations: " << counttree << endl; | ||
| hashtable.add(name, entered); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
если я правильно понял, то пользователь должен выбирать, в какую из таблиц он хочет положить полином
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
В задании написано "Работа происходит сразу с таблицами всех типов.", как я и сделал
test/CMakeLists.txt
Outdated
| file(GLOB hdrs "*.h*" "../include/*.h") | ||
| file(GLOB srcs "*.cpp") |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
зачем убрал "../src/*.cpp" ?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Да что с ним, что без него - не работает =)
include/AVLTreeTable.h
Outdated
|
|
||
| static int counttree = 0; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
так counttree работать не будет, ты либо прописываешь эту переменную в хедере как extern int counttree и в исходниках пишешь int counttree, либо помещаешь внутрь класса
при текущей реализации программа-сэмпл выводит 0 операций при вставке, поиске и удалении (что, очевидно, не так)
| } | ||
| try { | ||
| search(name); | ||
| } | ||
| catch (std::logic_error& e) { | ||
| Node* cur = head; | ||
| std::vector<Node*> path = memorysearch(name); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
интересная, конечно, схема с try/catch блоком...
если уж на то пошло, то в catch должно быть const std::exception& e
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
search выбрасывает logic_error, поэтому и ловится именно он
src/AVLTreeTable.cpp
Outdated
|
|
||
| polynoms AVLTreeTable::search(std::string name) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
неплохо бы возвращать не собственно полином, а указатель на cur->data.second
можно будет как минимум сделать проще проверку на наличие элемента в таблице
| if (i >= 1) { | ||
| if (s[i] == 'x' && (s[i - 1] == '0' || s[i - 1] == '1' || s[i - 1] == '2' || s[i - 1] == '3' || s[i - 1] == '4' || s[i - 1] == '5' || s[i - 1] == '6' || s[i - 1] == '7' || s[i - 1] == '8' || s[i - 1] == '9')) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
| if (i >= 1) { | |
| if (s[i] == 'x' && (s[i - 1] == '0' || s[i - 1] == '1' || s[i - 1] == '2' || s[i - 1] == '3' || s[i - 1] == '4' || s[i - 1] == '5' || s[i - 1] == '6' || s[i - 1] == '7' || s[i - 1] == '8' || s[i - 1] == '9')) { | |
| if (i >= 1) { | |
| if (s[i] == 'x' && s[i - 1] >= '0' && s[i - 1] <= '9') { |
так компактнее будет
| } | ||
| TEST(AVLTreeTable, can_clear) { | ||
| list<pair<int, double>>a; | ||
| a.push_back(make_pair(100, 1)); | ||
| polynoms A(a); | ||
| AVLTreeTable T; | ||
| T.add("pol", A); | ||
| ASSERT_NO_THROW(T.clear("pol")); | ||
| } | ||
| TEST(AVLTreeTable, clear_is_correct) { | ||
| list<pair<int, double>>a; | ||
| a.push_back(make_pair(100, 1)); | ||
| polynoms A(a); | ||
| AVLTreeTable T; | ||
| T.add("pol", A); | ||
| T.clear("pol"); | ||
| ASSERT_ANY_THROW(T.search("pol")); | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
можно добавить тесты на удаление с различными сценариями (удаление листа, вершины с одним или двумя потомками, головы с потомками или без потомков)
KorotinEgor
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Методы с арифметикой я не проверял, скажем, что они правильные изначально, а если это не так, то виноват госопдин проверяющий.
|
|
||
| class UnorderedTable { | ||
| std::vector<std::pair<std::string, polynoms>> table; | ||
| size_t size; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
А в чём вообще смысл этой переменной? Ты хранишь размер, чтобы, если что, выдать количество элементов пользователю за О(1), но с данной функцией прекрасно спровляется return table.size()
| this->add(rec.first, rec.second); | ||
| } | ||
| } | ||
| void UnorderedTable::add(std::string name, polynoms pol) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
В некоторых методах деревьев вроде бы поправил, а тут - нет. Лучше передавать что строку, что полином по ссылке, чтобы не копировать одно и то же по 10 раз
В хэшах и тех методах деревьев, что не попали под "некоторые" аналогично
include/HashTable.h
Outdated
| polynoms search(std::string name); | ||
| void add(std::string name, polynoms pol); | ||
| void clear(std::string name); | ||
| void resize(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
А разве не логичнее будет засунуть resize в private? А так, это нарушение принципов ООП
| int res, strsum = 0; | ||
| for (int i = 0; i < name.size(); i++) { | ||
| strsum += int(name[i]); | ||
| } | ||
| res = strsum % size; | ||
| return res; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
А зачем res вообще существует?, то же можно сказать и про Hash2.
| if (table[(Hash1(name) + i * Hash2(name)) % size] != nullptr) { | ||
| if (table[(Hash1(name) + i * Hash2(name)) % size]->state == 0 || table[(Hash1(name) + i * Hash2(name)) % size]->state == -1) { | ||
| table[(Hash1(name) + i * Hash2(name)) % size] = new Rec(name, pol); | ||
| return; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Утечка памяти, если элемент явяется удалённым ты просто присваиваешь в Table[...] новый указатель, в то время как старый элемент, на который там раньше был указатель остаётся где-то непонятно где, но точно не удаляется.
| while (true) { | ||
| counttree++; | ||
| if (name < cur->data.first) { | ||
| if (cur->left) { | ||
| cur->h += 1; | ||
| cur = cur->left; | ||
| } | ||
| else { | ||
| break; | ||
| } | ||
| } | ||
| else { | ||
| if (cur->right) { | ||
| cur->h += 1; | ||
| cur = cur->right; | ||
| } | ||
| else { | ||
| break; | ||
| } | ||
| } | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Не понял смысл этого действия, разве нельзя просто пройтись по path и всем там h++ сделать?
| else { | ||
|
|
||
| if (balance(path[i]) == 2) { | ||
| if (balance(path[i]->left) >= 0) { | ||
| if (i == 0) smallrightrot(nullptr, path[i]); | ||
| else smallrightrot(path[i - 1], path[i]); | ||
| } | ||
| else if (balance(path[i]->left) < 0) { | ||
| if (i == 0) bigrightrot(nullptr, path[i]); | ||
| else bigrightrot(path[i - 1], path[i]); | ||
| } | ||
| } | ||
| if (balance(path[i]) == -2) { | ||
| if (balance(path[i]->right) <= 0) { | ||
| if (i == 0) smallleftrot(nullptr, path[i]); | ||
| else smallleftrot(path[i - 1], path[i]); | ||
| } | ||
| else if (balance(path[i]->right) > 0) { | ||
| if (i == 0) bigleftrot(nullptr, path[i]); | ||
| else bigleftrot(path[i - 1], path[i]); | ||
| } | ||
| } | ||
| seth(path[i]); | ||
|
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Эта часть бесполезна, как и весь этот огромный if, его единтсенное теоретичсекое предназначение - чтоб не залесть, куда не надо, но в твоём случае, это опбеспечивает метод balance (в него уже встроена проверка на то, являются ли 1 или 2 потомка нулевыми или нет)
include/AVLTreeTable.h
Outdated
| void smallleftrot(Node* xparent, Node* x); | ||
| void smallrightrot(Node* xparent, Node* x); | ||
| void bigleftrot(Node* xparent, Node* x); | ||
| void bigrightrot(Node* xparent, Node* x); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
повороты должны быть в private, тк они могут изменить дерево так, что оно перестанет быть AVL-деревом или, могут уронить программу(при попытке прочитать не принадлежащую им память), чего ты, как разработчик классов на C++, допускать не должен.
| else if (minval->left != nullptr && minval->right == nullptr) { | ||
| path[path.size() - 2]->right == minval->left; | ||
| counttree++; | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
опять бесполезная часть, после цикла while у cur никогда нет потомков слева, т.е. minnval->left=nullptr всегда
| else { | ||
| counttree++; | ||
| if (path[path.size() - 2]->left == cur) { | ||
| path[path.size() - 2]->left = cur->left; | ||
| } | ||
| else { | ||
| path[path.size() - 2]->right = cur->left; | ||
| } | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Не рассмтариваешь случай, когда у тебя дерево это голова с 1м левым потомком и ты хочешь удалить голову. Тогда path.size()=1, path[path.size() - 1]->h!=0, cur->right==nullptr, ты попадаешь в это место и деалешь path[path.size() - 2]
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Кроме того, если ты попал сюда, то ты даже не удаляешь cur, а просто исключешь его из дерева, т.е. ещё одна утечка памяти
|
@ValentinV95, Здравствуйте, код готов к проверке |
ValentinV95
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Лабораторная принята, часть справидливых замечаний от одногруппников осталась не исправленной и не прокомментирована
No description provided.