Функция dictionary_select
возвращает вектор, который содержит слова, начинающиеся с W. В этом коде dictionary_select
появляется сообщение об ошибке. Но я не могу его найти. Кто-нибудь может мне помочь?
#include <iostream>
#include <string>
#include <vector>
using namespace std;
struct tree {
string data;
tree *left;
tree *right;
};
typedef tree* dictionary;
bool dictionary_ins_word(dictionary & D, const string & W)
{
if(W == "" || W == " ")
return false;
tree* dic;
dic = new tree;
dic->data = W;
dic->left = NULL;
dic->right = NULL;
if(D == NULL) {
D = dic;
}
else {
if(W <= D->data)
dictionary_ins_word(D->left, W);
else
dictionary_ins_word(D->right, W);
}
return true;
}
bool dictionary_lookup(const dictionary & D, const string & W)
{
if(W == "" || W == " ")
return false;
if(D == NULL)
return false;
if(W == D->data)
return true;
else if (W < D->data)
return dictionary_lookup(D->left, W);
else
return dictionary_lookup(D->right, W);
}
bool dictionary_is_empty(const dictionary & D)
{
if(D == NULL)
return true;
else
return false;
}
bool dictionary_del_word(dictionary & D, const string & W)
{
if(!dictionary_lookup(D, W))
return false;
if(W < D->data)
dictionary_del_word(D->left, W);
else if(W > D->data)
dictionary_del_word(D->right, W);
else {
string item;
tree* temp;
temp = D;
if(D->left == NULL) {
D = D->right;
delete temp;
}
else if(D->right == NULL) {
D = D->left;
delete temp;
}
else {
while(D->left->right != NULL)
D->left = D->left->right;
item = D->left->data;
D->data = item;
dictionary_del_word(D->left, W);
}
}
return true;
}
bool dictionary_min(string & W, const dictionary & D)
{
dictionary min;
if(D == NULL)
return false;
min = D;
while(min->left != NULL)
min = min->left;
W = min->data;
return true;
}
vector <string> dictionary_select(const dictionary & D, const string & W)
{
vector < string > result;
vector < string > zeroVec;
string temp;
zeroVec.push_back("");
if(D == NULL)
return zeroVec;
temp = D->data;
size_t found = temp.find(W);
if(found == 0)
result.push_back(D->data);
if(W <= D->data)
return dictionary_select(D->left, W);
else
return dictionary_select(D->right, W);
}
int main()
{
bool b[5];
dictionary l;
string W, str;
vector <string> vec;
l = new tree;
l->data = "berdi";
l->left = NULL;
l->right = NULL;
b[0] = dictionary_ins_word(l, "atas");
b[1] = dictionary_ins_word(l, "cara");
b[2] = dictionary_ins_word(l, "ata");
b[3] = dictionary_ins_word(l, "atax");
vec = dictionary_select(l, "ata");
for(int i=0; i<vec.size(); i++) {
cout << vec[i] << " ";
}
getchar();
return 0;
}
Проблема заключается в том, что ваша функция dictionary_select объявляет вектор результата и никогда не возвращает его. Ниже вы можете изменить это:
vector <string> dictionary_select(const dictionary & D, const string & W)
{
vector < string > result;
vector < string > tempVector; // add this to store the result from the recursion
vector < string > zeroVec;
string temp;
zeroVec.push_back("");
if(D == NULL)
return zeroVec;
temp = D->data;
size_t found = temp.find(W);
if(found == 0)
result.push_back(D->data);
if(W <= D->data)
tempVector = dictionary_select(D->left, W); // get the recursion result
else
tempVector = dictionary_select(D->right, W); // get the recursion result
result.insert(result.end(), tempVector.begin(), tempVector.end()); // append all the results
return result; // return the result
}
ОБНОВИТЬ
Чтобы функция возвращала правильные данные, вы также должны убедиться, что вы смотрите на левую и правую стороны дерева, чтобы получить соответствующие результаты. Ниже приведена функция:
vector <string> dictionary_select(const dictionary & D, const string & W)
{
vector < string > result;
vector < string > tempVectorLeft; // add this to store the result from the left recursion
vector < string > tempVectorRight; // add this to store the result from the right recursion
vector < string > zeroVec;
string temp;
zeroVec.push_back("");
if(D == NULL)
return zeroVec;
temp = D->data;
size_t found = temp.find(W);
if(found == 0)
result.push_back(D->data);
if(found == 0 || W <= D->data)
tempVectorLeft = dictionary_select(D->left, W); // store results
if(found == 0 || W > D->data)
tempVectorRight = dictionary_select(D->right, W); // store results
result.insert(result.end(), tempVectorLeft.begin(), tempVectorLeft.end()); // append all the left results
result.insert(result.end(), tempVectorRight.begin(), tempVectorRight.end()); // append all the right results
return result;
}
Предлагаю вам следующий вариант:
vector <string> dictionary_select(const dictionary & D, const string & W)
{
vector < string > result;
vector < string > zeroVec;
if (D == NULL)
return zeroVec;
string temp = D->data;
size_t found = temp.find(W);
if (found == 0)
result.push_back(D->data);
if (found || W <= D->data)
for(auto x: dictionary_select(D->left, W))
result.push_back(x);
if (found || W > D->data)
for (auto x : dictionary_select(D->right, W))
result.push_back(x);
return result;
}
Проблема в методе if
/else
используемая в вашем первоначальном algortihm для выбора между рекурсией на левом или правом узле, заключается в том, что вы можете иметь такую заметку:
atar
/ \
ata atax
Поэтому, если данные в головке узла совпадают, вам нужно проверить как слева, так и справа, чтобы убедиться, что вы что-то не упустили.