私はバイナリ検索ツリー内に後継ノードと先行ノードを取得する方法がありますが、私のコードでそのバグを見つけるのに問題があります。次のキーを持つノードを追加します:"C"
、"B"
、および"K"
。私は、バイナリ検索ツリーの内容を印刷する場合、私は次のような出力が得られます。先行ノードと後継ノードの検索
"C" "some data 1"
"B" "some data 2"
"K" "some data 3"
私は"B"
を追加すると、それは明らかに何の先行または後続を持っていないので、私はちょうど空の文字列にそれらの設定:
root = root->insert(root, key, data);
root->getNextAndPrev(root, prev, next, key);
string p;
string n;
if (!prev) {
pred = "";
}
else {
pred = prev->getKey();
}
if (!next) {
succ = "";
}
else {
succ = next->getKey();
}
return new Entry(data, succ, pred);
を
"B"
を追加すると、"B"
の後継者が"C"
で、前任者が期待通りに""
であるという出力が得られます。しかし、ツリーに"K"
を追加すると、"K"
の前身は"C"
で、後継者も"C"
という出力が得られます。なぜ私は何か後継者がないかどうかを確認するためにチェックしているので、なぜこのエラーが出るのか分かりません(何も来ていません。"K"
)空の文字列に設定してください。
マイNode
クラスはinsert()
とgetNextAndPrev()
メソッドを処理し、ここで私はそれらを実装してきた方法です:
void Node::getNextAndPrev(Node* root, string key) {
if (!root) return;
if (root->key == key){
if (root->left != NULL){
Node* tempNode = root->left;
while (tempNode->right != NULL) {
tempNode = tempNode->right;
}
prev= tempNode;
}
if (root->right != NULL){
Node* tempNode = root->right;
while (tempNode->left != NULL) {
tempNode = tempNode->left;
}
next = tempNode;
}
}
if (root->key > key) {
next = root;
getNextAndPrev(root->left, key);
}
else {
prev = root;
getNextAndPrev(root->right, key);
}
}
それは順不同でいくつかのキーを追加して、私のgetNextAndPrev
を引き起こすことがあるのはなぜ間違った値を取得するには?
恐らくそれは私のエントリをどのように私のmain
に挿入しているかと関係があります。私は次のように設定したループを持っている:
string command = "";
Entry* entry = new Entry("","","");
string def = "";
while (true) {
cout << "Enter command: ";
getline(cin, command);
if (parseCommand(command, "ADD") == 0) {
string tempCmd = processCommand(command, 3);
string key = tempCmd.substr(0, tempCmd.length() - 4);
string data = tempCmd.substr(tempCmd.length() - 4);
trim(key);
trim(data);
def = data;
entry = dict->modify(key, data);
cout << "added: " << key << " with definition of : " << def << " to the dictionary " << endl;
}
modify()
が私のDictionary
クラス内そうのように呼び出されます:
Entry * Dictionary::modify(string key, string data) {
Entry * entry = new Entry("","","");
if (root) entry = search(key);
//inserting something into the dictionary
if (data != "" && !this->root->doesContain(this->root, key)) {
root = root->insert(root, key, data);
return entry;
}
}
そして最後に、modify()
内部で呼び出される私のsearch()
方法:
Entry * Dictionary::search(string key) {
if (key == "") {
return new Entry("", getSmallestKey(), getLargestKey());
}
if (!this->root->doesContain(root, key)) {
root->getNextAndPrev(root, key);
string prev;
string next;
if (root->getPrevNode() != NULL) {
prev = root->getPrevious();
cout << "Predecessor is " << prev << " root is: " << root->getKey() << endl;
}
else {
prev = "";
cout << "No Predecessor" << endl;
}
if (root->getNextNode() != NULL) {
next = root->getNext();
cout << "Successor is " << next << " root is: " << root->getKey() << endl;
}
else {
next = "";
cout << "No Successor" << endl;
}
if (next == prev) {
if (next < key) {
next = "";
}
if (prev > key) {
prev = "";
}
}
return new Entry("", next, prev);
}
問題を詳細に説明するために、上記の実行結果を以下に示します。
Enter command: ADD "FOO" "D" lookup stuff: root: prev: next: // gets logged out when I insert into dictionary added: "FOO" with a definition of: "D" to the dictionary Enter command: ADD "BIN" "C" No Predecessor Successor is "FOO" root is: "FOO" lookup stuff: root: prev: next: "FOO" added: "BIN" with a definition of: "C" to the dictionary Enter command: ADD "QUUX" "D" Predecessor is "FOO" root is: "FOO" Successor is "FOO" root is: "FOO" lookup stuff: root: prev: "FOO" next: added: "QUUX" with a definition of: "D" to the dictionary Enter command: ADD "BAZ" "N" Predecessor is "FOO" root is: "FOO" Successor is "BIN" root is: "FOO" lookup stuff: root: prev: "FOO" next: "BIN" added: "BAZ" with a definition of: "N" to the dictionary
辞書にBAZ
を追加するとき、前任者と後継者が場違い今、なぜ私が理解することはできません。
Enter command: ADD "BAZ" "N" Predecessor is "FOO" root is: "FOO" Successor is "BIN" root is: "FOO"
@SummetSingh私の質問を、私のプログラムの動作をさらに説明するために、私の 'main'の出力から更新しました。また、 'getNextAndPrev()'は、前と同じようにnextとpreviousの参照を渡すのではなく、通常のgetterを使って次の値と前の値を取得します。 –