Некоторые проблемы с вашим кодом: ваш treeSuccessor
начинается с
if (x.right == null){
return treeMinimum(x.right);
}
что должно быть if (x.right != null)
, конечно.
Ваш код insert
имеет строки
Node tmp = getParent(t,z);
tmp = y;
, где вы назначаете tmp
и немедленно назначаете его снова. Мне не кажется, что вам нужны эти строки вообще, так как вы не используете tmp
в дальнейшем. В этот момент у вас есть y
узел, в чей дочерний элемент вставляется z
, поэтому просто удалите эти строки.
Опять же, в delete
у вас есть строки
if (x != null){
Node tmp = getParent(t,x);
tmp = getParent(t,y);
}
, где вы на самом деле ничего не делаете, поскольку tmp
не виден вне этого фрагмента. И далее, в delete
вы повторяете выражение getParent(t,y)
, которое может быть дорогостоящей операцией, поэтому вы должны вычислить его только один раз и присвоить его некоторой переменной.
Но в целом ваш код, хотя он и кажется правильным (возможно, кроме delete
, который я не совсем понял, но который выглядит подозрительно), мало похож на типичный двоичный код дерева. Вам на самом деле не нужны методы getParent
и treeSuccessor
для реализации search
, insert
и delete
. Базовая структура, которая у вас есть для search
, работает и для других, со следующими модификациями:
- с
insert
, когда вы получаете ссылку null
вместо возврата null
, вставьте элемент в эту точку
- с
delete
, когда вы найдете элемент, если у него есть только один (или нет) дочерний элемент, замените его на этот дочерний элемент, и, если у него есть два дочерних элемента, замените его либо максимумом левого дочернего дерева, либо минимум правильного дочернего дерева
Оба из них требуют, кроме того, чтобы вы отслеживали родительский узел при спуске в дерево, но это единственное изменение, которое вам нужно внести в search
. В частности, никогда не нужно подниматься вверх по дереву (что сделает treeSuccessor
).