Напишите функцию для соединения всех смежных узлов на одном уровне в двоичном дереве. Структура данного узла двоичного дерева выглядит следующим образом.
struct node {
int data;
struct node* left;
struct node* right;
struct node* nextRight;
}
|
Изначально все указатели nextRight указывают на значения мусора. Ваша функция должна установить эти указатели так, чтобы они указывали следующий справа для каждого узла. Вы можете использовать только постоянное дополнительное пространство.
Пример:
Input Tree
A
/ \
B C
/ \ \
D E F
Output Tree
A--->NULL
/ \
B-->C-->NULL
/ \ \
D-->E-->F-->NULL
Мы обсудили два разных подхода к этому в предыдущем посте . Вспомогательное пространство, необходимое в обоих этих подходах, не является постоянным. Кроме того, описанный там метод 2 работает только для полного двоичного дерева.
В этой статье мы сначала изменим метод 2, чтобы он работал для всех видов деревьев. После этого мы удалим рекурсию из этого метода, чтобы дополнительное пространство стало постоянным.
Рекурсивное решение
В методе 2 предыдущего поста мы прошли узлы в порядке предварительного заказа. Вместо обхода в порядке предварительного заказа (root, left, right), если мы пройдем узел nextRight до левого и правого потомка (root, nextRight, left), то мы можем убедиться, что все узлы на уровне i имеют значение nextRight. До уровня я + 1 узлов. Давайте рассмотрим следующий пример (тот же пример, что и в предыдущем посте ). Метод 2 завершается неудачно для правого потомка узла 4. В этом методе мы проверяем, что все узлы на уровне 4 (уровень 2) имеют значение nextRight, прежде чем мы попытаемся установить значение nextRight, равное 9. Поэтому, когда мы устанавливаем nextRight из 9, мы ищем нелистный узел на правой стороне узла 4 (getNextRight () делает это для нас).
1 -------------- Level 0
/ \
2 3 -------------- Level 1
/ \ / \
4 5 6 7 -------------- Level 2
/ \ / \
8 9 10 11 -------------- Level 3
С
void connectRecur( struct node* p);
struct node *getNextRight( struct node *p);
void connect ( struct node *p)
{
p->nextRight = NULL;
connectRecur(p);
}
void connectRecur( struct node* p)
{
if (!p)
return ;
if (p->nextRight != NULL)
connectRecur(p->nextRight);
if (p->left)
{
if (p->right)
{
p->left->nextRight = p->right;
p->right->nextRight = getNextRight(p);
}
else
p->left->nextRight = getNextRight(p);
connectRecur(p->left);
}
else if (p->right)
{
p->right->nextRight = getNextRight(p);
connectRecur(p->right);
}
else
connectRecur(getNextRight(p));
}
struct node *getNextRight( struct node *p)
{
struct node *temp = p->nextRight;
while (temp != NULL)
{
if (temp->left != NULL)
return temp->left;
if (temp->right != NULL)
return temp->right;
temp = temp->nextRight;
}
return NULL;
}
|
Джава
class Node
{
int data;
Node left, right, nextRight;
Node( int item)
{
data = item;
left = right = nextRight = null ;
}
}
class BinaryTree
{
Node root;
void connectRecur(Node p)
{
if (p == null )
return ;
if (p.nextRight != null )
connectRecur(p.nextRight);
if (p.left != null )
{
if (p.right != null )
{
p.left.nextRight = p.right;
p.right.nextRight = getNextRight(p);
}
else
p.left.nextRight = getNextRight(p);
connectRecur(p.left);
}
else if (p.right != null )
{
p.right.nextRight = getNextRight(p);
connectRecur(p.right);
}
else
connectRecur(getNextRight(p));
}
Node getNextRight(Node p)
{
Node temp = p.nextRight;
while (temp != null )
{
if (temp.left != null )
return temp.left;
if (temp.right != null )
return temp.right;
temp = temp.nextRight;
}
return null ;
}
public static void main(String args[])
{
BinaryTree tree = new BinaryTree();
tree.root = new Node( 10 );
tree.root.left = new Node( 8 );
tree.root.right = new Node( 2 );
tree.root.left.left = new Node( 3 );
tree.root.right.right = new Node( 90 );
tree.connectRecur(tree.root);
int a = tree.root.nextRight != null ?
tree.root.nextRight.data : - 1 ;
int b = tree.root.left.nextRight != null ?
tree.root.left.nextRight.data : - 1 ;
int c = tree.root.right.nextRight != null ?
tree.root.right.nextRight.data : - 1 ;
int d = tree.root.left.left.nextRight != null ?
tree.root.left.left.nextRight.data : - 1 ;
int e = tree.root.right.right.nextRight != null ?
tree.root.right.right.nextRight.data : - 1 ;
System.out.println( "Following are populated nextRight pointers in "
+ " the tree(-1 is printed if there is no nextRight)" );
System.out.println( "nextRight of " + tree.root.data + " is " + a);
System.out.println( "nextRight of " + tree.root.left.data + " is " + b);
System.out.println( "nextRight of " + tree.root.right.data + " is " + c);
System.out.println( "nextRight of " + tree.root.left.left.data +
" is " + d);
System.out.println( "nextRight of " + tree.root.right.right.data +
" is " + e);
}
}
|
C #
using System;
public class Node
{
public int data;
public Node left, right, nextRight;
public Node( int item)
{
data = item;
left = right = nextRight = null ;
}
}
public class BinaryTree
{
public Node root;
public virtual void connectRecur(Node p)
{
if (p == null )
{
return ;
}
if (p.nextRight != null )
{
connectRecur(p.nextRight);
}
if (p.left != null )
{
if (p.right != null )
{
p.left.nextRight = p.right;
p.right.nextRight = getNextRight(p);
}
else
{
p.left.nextRight = getNextRight(p);
}
connectRecur(p.left);
}
else if (p.right != null )
{
p.right.nextRight = getNextRight(p);
connectRecur(p.right);
}
else
{
connectRecur(getNextRight(p));
}
}
public virtual Node getNextRight(Node p)
{
Node temp = p.nextRight;
while (temp != null )
{
if (temp.left != null )
{
return temp.left;
}
if (temp.right != null )
{
return temp.right;
}
temp = temp.nextRight;
}
return null ;
}
public static void Main( string [] args)
{
BinaryTree tree = new BinaryTree();
tree.root = new Node(10);
tree.root.left = new Node(8);
tree.root.right = new Node(2);
tree.root.left.left = new Node(3);
tree.root.right.right = new Node(90);
tree.connectRecur(tree.root);
int a = tree.root.nextRight != null ? tree.root.nextRight.data : -1;
int b = tree.root.left.nextRight != null ? tree.root.left.nextRight.data : -1;
int c = tree.root.right.nextRight != null ? tree.root.right.nextRight.data : -1;
int d = tree.root.left.left.nextRight != null ? tree.root.left.left.nextRight.data : -1;
int e = tree.root.right.right.nextRight != null ? tree.root.right.right.nextRight.data : -1;
Console.WriteLine( "Following are populated nextRight pointers in the tree(-1 is printed if there is no nextRight)" );
Console.WriteLine( "nextRight of " + tree.root.data + " is " + a);
Console.WriteLine( "nextRight of " + tree.root.left.data + " is " + b);
Console.WriteLine( "nextRight of " + tree.root.right.data + " is " + c);
Console.WriteLine( "nextRight of " + tree.root.left.left.data + " is " + d);
Console.WriteLine( "nextRight of " + tree.root.right.right.data + " is " + e);
}
}
|
Выход:
Following are populated nextRight pointers in the tree (-1 is printed if
there is no nextRight)
nextRight of 10 is -1
nextRight of 8 is 2
nextRight of 2 is -1
nextRight of 3 is 90
nextRight of 90 is -1
Итеративное решение
Рассмотренный выше рекурсивный подход может быть легко преобразован в итеративный. В итерационной версии мы используем вложенный цикл. Внешний цикл проходит через все уровни, а внутренний цикл проходит через все узлы на каждом уровне. Это решение использует постоянное пространство.
C ++
#include<bits/stdc++.h> #include<iostream>
using namespace std;
class node
{
public :
int data;
node* left;
node* right;
node *nextRight;
node( int data)
{
this ->data = data;
this ->left = NULL;
this ->right = NULL;
this ->nextRight = NULL;
}
};
node *getNextRight(node *p) {
node *temp = p->nextRight;
while (temp != NULL)
{
if (temp->left != NULL)
return temp->left;
if (temp->right != NULL)
return temp->right;
temp = temp->nextRight;
}
return NULL;
}
void connectRecur(node* p)
{
node *temp;
if (!p)
return ;
p->nextRight = NULL;
while (p != NULL)
{
node *q = p;
while (q != NULL)
{
if (q->left)
{
if (q->right)
q->left->nextRight = q->right;
else
q->left->nextRight = getNextRight(q);
}
if (q->right)
q->right->nextRight = getNextRight(q);
q = q->nextRight;
}
if (p->left)
p = p->left;
else if (p->right)
p = p->right;
else
p = getNextRight(p);
}
}
int main()
{
node *root = new node(10);
root->left = new node(8);
root->right = new node(2);
root->left->left = new node(3);
root->right->right = new node(90);
connectRecur(root);
cout << "Following are populated nextRight pointers in the tree"
" (-1 is printed if there is no nextRight) \n" ;
cout << "nextRight of " << root->data << " is "
<< (root->nextRight? root->nextRight->data: -1) <<endl;
cout << "nextRight of " << root->left->data << " is "
<< (root->left->nextRight? root->left->nextRight->data: -1) << endl;
cout << "nextRight of " << root->right->data << " is "
<< (root->right->nextRight? root->right->nextRight->data: -1) << endl;
cout << "nextRight of " << root->left->left->data<< " is "
<< (root->left->left->nextRight? root->left->left->nextRight->data: -1) << endl;
cout << "nextRight of " << root->right->right->data << " is "
<< (root->right->right->nextRight? root->right->right->nextRight->data: -1) << endl;
return 0;
}
|
С
#include <stdio.h> #include <stdlib.h>
struct node
{
int data;
struct node *left;
struct node *right;
struct node *nextRight;
};
struct node *getNextRight( struct node *p)
{
struct node *temp = p->nextRight;
while (temp != NULL)
{
if (temp->left != NULL)
return temp->left;
if (temp->right != NULL)
return temp->right;
temp = temp->nextRight;
}
return NULL;
}
void connect( struct node* p)
{
struct node *temp;
if (!p)
return ;
p->nextRight = NULL;
while (p != NULL)
{
struct node *q = p;
while (q != NULL)
{
if (q->left)
{
if (q->right)
q->left->nextRight = q->right;
else
q->left->nextRight = getNextRight(q);
}
if (q->right)
q->right->nextRight = getNextRight(q);
q = q->nextRight;
}
if (p->left)
p = p->left;
else if (p->right)
p = p->right;
else
p = getNextRight(p);
}
}
struct node* newnode( int data)
{
struct node* node = ( struct node*)
malloc ( sizeof ( struct node));
node->data = data;
node->left = NULL;
node->right = NULL;
node->nextRight = NULL;
return (node);
}
int main()
{
struct node *root = newnode(10);
root->left = newnode(8);
root->right = newnode(2);
root->left->left = newnode(3);
root->right->right = newnode(90);
connect(root);
printf ( "Following are populated nextRight pointers in the tree "
"(-1 is printed if there is no nextRight) \n" );
printf ( "nextRight of %d is %d \n" , root->data,
root->nextRight? root->nextRight->data: -1);
printf ( "nextRight of %d is %d \n" , root->left->data,
root->left->nextRight? root->left->nextRight->data: -1);
printf ( "nextRight of %d is %d \n" , root->right->data,
root->right->nextRight? root->right->nextRight->data: -1);
printf ( "nextRight of %d is %d \n" , root->left->left->data,
root->left->left->nextRight? root->left->left->nextRight->data: -1);
printf ( "nextRight of %d is %d \n" , root->right->right->data,
root->right->right->nextRight? root->right->right->nextRight->data: -1);
getchar ();
return 0;
}
|
Джава
class Node
{
int data;
Node left, right, nextRight;
Node( int item)
{
data = item;
left = right = nextRight = null ;
}
}
class BinaryTree
{
Node root;
Node getNextRight(Node p)
{
Node temp = p.nextRight;
while (temp != null )
{
if (temp.left != null )
return temp.left;
if (temp.right != null )
return temp.right;
temp = temp.nextRight;
}
return null ;
}
void connect(Node p) {
Node temp = null ;
if (p == null )
return ;
p.nextRight = null ;
while (p != null )
{
Node q = p;
while (q != null )
{
if (q.left != null )
{
if (q.right != null )
q.left.nextRight = q.right;
else
q.left.nextRight = getNextRight(q);
}
if (q.right != null )
q.right.nextRight = getNextRight(q);
q = q.nextRight;
}
if (p.left != null )
p = p.left;
else if (p.right != null )
p = p.right;
else
p = getNextRight(p);
}
}
public static void main(String args[])
{
BinaryTree tree = new BinaryTree();
tree.root = new Node( 10 );
tree.root.left = new Node( 8 );
tree.root.right = new Node( 2 );
tree.root.left.left = new Node( 3 );
tree.root.right.right = new Node( 90 );
tree.connect(tree.root);
int a = tree.root.nextRight != null ?
tree.root.nextRight.data : - 1 ;
int b = tree.root.left.nextRight != null ?
tree.root.left.nextRight.data : - 1 ;
int c = tree.root.right.nextRight != null ?
tree.root.right.nextRight.data : - 1 ;
int d = tree.root.left.left.nextRight != null ?
tree.root.left.left.nextRight.data : - 1 ;
int e = tree.root.right.right.nextRight != null ?
tree.root.right.right.nextRight.data : - 1 ;
System.out.println( "Following are populated nextRight pointers in "
+ " the tree(-1 is printed if there is no nextRight)" );
System.out.println( "nextRight of " + tree.root.data + " is " + a);
System.out.println( "nextRight of " + tree.root.left.data
+ " is " + b);
System.out.println( "nextRight of " + tree.root.right.data +
" is " + c);
System.out.println( "nextRight of " + tree.root.left.left.data +
" is " + d);
System.out.println( "nextRight of " + tree.root.right.right.data +
" is " + e);
}
}
|
python3
class newnode:
def __init__( self ,data):
self .data = data
self .left = None
self .right = None
self .nextRight = None
def getNextRight(p):
temp = p.nextRight
while (temp ! = None ):
if (temp.left ! = None ):
return temp.left
if (temp.right ! = None ):
return temp.right
temp = temp.nextRight
return None
def connect(p):
temp = None
if ( not p):
return
p.nextRight = None
while (p ! = None ):
q = p
while (q ! = None ):
if (q.left):
if (q.right):
q.left.nextRight = q.right
else :
q.left.nextRight = getNextRight(q)
if (q.right):
q.right.nextRight = getNextRight(q)
q = q.nextRight
if (p.left):
p = p.left
elif (p.right):
p = p.right
else :
p = getNextRight(p)
if __name__ = = '__main__' :
root = newnode( 10 )
root.left = newnode( 8 )
root.right = newnode( 2 )
root.left.left = newnode( 3 )
root.right.right = newnode( 90 )
connect(root)
print ( "Following are populated nextRight "
"pointers in the tree (-1 is printed "
"if there is no nextRight) \n" )
print ( "nextRight of" , root.data,
"is" , end = " " )
if root.nextRight:
print (root.nextRight.data)
else :
print ( - 1 )
print ( "nextRight of" , root.left.data,
"is" , end = " " )
if root.left.nextRight:
print (root.left.nextRight.data)
else :
print ( - 1 )
print ( "nextRight of" , root.right.data,
"is" , end = " " )
if root.right.nextRight:
print (root.right.nextRight.data)
else :
print ( - 1 )
print ( "nextRight of" , root.left.left.data,
"is" , end = " " )
if root.left.left.nextRight:
print (root.left.left.nextRight.data)
else :
print ( - 1 )
print ( "nextRight of" , root.right.right.data,
"is" , end = " " )
if root.right.right.nextRight:
print (root.right.right.nextRight.data)
else :
print ( - 1 )
|
C #
using System;
public class Node
{
public int data;
public Node left, right, nextRight;
public Node( int item)
{
data = item;
left = right = nextRight = null ;
}
}
public class BinaryTree
{
public Node root;
public virtual Node getNextRight(Node p)
{
Node temp = p.nextRight;
while (temp != null )
{
if (temp.left != null )
{
return temp.left;
}
if (temp.right != null )
{
return temp.right;
}
temp = temp.nextRight;
}
return null ;
}
public virtual void connect(Node p)
{
Node temp = null ;
if (p == null )
{
return ;
}
p.nextRight = null ;
while (p != null )
{
Node q = p;
while (q != null )
{
if (q.left != null )
{
if (q.right != null )
{
q.left.nextRight = q.right;
}
else
{
q.left.nextRight = getNextRight(q);
}
}
if (q.right != null )
{
q.right.nextRight = getNextRight(q);
}
q = q.nextRight;
}
if (p.left != null )
{
p = p.left;
}
else if (p.right != null )
{
p = p.right;
}
else
{
p = getNextRight(p);
}
}
}
public static void Main( string [] args)
{
BinaryTree tree = new BinaryTree();
tree.root = new Node(10);
tree.root.left = new Node(8);
tree.root.right = new Node(2);
tree.root.left.left = new Node(3);
tree.root.right.right = new Node(90);
tree.connect(tree.root);
int a = tree.root.nextRight != null ? tree.root.nextRight.data : -1;
int b = tree.root.left.nextRight != null ? tree.root.left.nextRight.data : -1;
int c = tree.root.right.nextRight != null ? tree.root.right.nextRight.data : -1;
int d = tree.root.left.left.nextRight != null ? tree.root.left.left.nextRight.data : -1;
int e = tree.root.right.right.nextRight != null ? tree.root.right.right.nextRight.data : -1;
Console.WriteLine( "Following are populated nextRight pointers in " + " the tree(-1 is printed if there is no nextRight)" );
Console.WriteLine( "nextRight of " + tree.root.data + " is " + a);
Console.WriteLine( "nextRight of " + tree.root.left.data + " is " + b);
Console.WriteLine( "nextRight of " + tree.root.right.data + " is " + c);
Console.WriteLine( "nextRight of " + tree.root.left.left.data + " is " + d);
Console.WriteLine( "nextRight of " + tree.root.right.right.data + " is " + e);
}
}
|
Выход:
Following are populated nextRight pointers in the tree (-1 is printed if
there is no nextRight)
nextRight of 10 is -1
nextRight of 8 is 2
nextRight of 2 is -1
nextRight of 3 is 90
nextRight of 90 is -1
Пожалуйста, пишите комментарии, если вы обнаружите что-то неправильное или вы хотите поделиться дополнительной информацией по обсуждаемой выше теме.
Рекомендуемые посты:
Соединяйте узлы на одном уровне, используя постоянное дополнительное пространство
0.00 (0%) 0 votes