05907: 二叉树的操作
http://cs101.openjudge.cn/practice/05907/
给定一棵二叉树,在二叉树上执行两个操作:
- 节点交换
把二叉树的两个节点交换。 
- 前驱询问
询问二叉树的一个节点对应的子树最左边的节点。 
输入
第一行输出一个整数t(t <= 100),代表测试数据的组数。
对于每组测试数据,第一行输入两个整数n m,n代表二叉树节点的个数,m代表操作的次数。
随后输入n行,每行包含3个整数X Y Z,对应二叉树一个节点的信息。X表示节点的标识,Y表示其左孩子的标识,Z表示其右孩子的标识。
再输入m行,每行对应一次操作。每次操作首先输入一个整数type。
当type=1,节点交换操作,后面跟着输入两个整数x y,表示将标识为x的节点与标识为y的节点交换。输入保证对应的节点不是祖先关系。
当type=2,前驱询问操作,后面跟着输入一个整数x,表示询问标识为x的节点对应子树最左的孩子。
1<=n<=100,节点的标识从0到n-1,根节点始终是0. m<=100
输出
对于每次询问操作,输出相应的结果。
样例输入
2
5 5
0 1 2
1 -1 -1
2 3 4
3 -1 -1
4 -1 -1
2 0
1 1 2
2 0
1 3 4
2 2
3 2
0 1 2
1 -1 -1
2 -1 -1
1 1 2
2 0样例输出
1
3
4
2用字典+列表的确比类方便
python
# 数学科学学院 王镜廷 2300010724
def find_leftmost_node(son, u):
while son[u][0] != -1:
u = son[u][0]
return u
def main():
t = int(input())
for _ in range(t):
n, m = map(int, input().split())
son = [-1] * (n + 1) # 存储每个节点的子节点
parent = {} # 存储每个节点的父节点和方向,{节点: (父节点, 方向)}
for _ in range(n):
i, u, v = map(int, input().split())
son[i] = [u, v]
parent[u] = (i, 0) # 左子节点
parent[v] = (i, 1) # 右子节点
for _ in range(m):
s = input().split()
if s[0] == "1":
u, v = map(int, s[1:])
fu, diru = parent[u]
fv, dirv = parent[v]
son[fu][diru] = v
son[fv][dirv] = u
parent[v] = (fu, diru)
parent[u] = (fv, dirv)
elif s[0] == "2":
u = int(s[1])
root = find_leftmost_node(son, u)
print(root)
if __name__ == "__main__":
main()python
# 23n2300011072 蒋子轩
def swap(x, y):
tree[loc[x][0]][loc[x][1]] = y
tree[loc[y][0]][loc[y][1]] = x
loc[x], loc[y] = loc[y], loc[x]
for _ in range(int(input())):
n, m = map(int, input().split())
tree = {}
loc = [[] for _ in range(n)]
for _ in range(n):
a, b, c = map(int, input().split())
tree[a] = [b, c]
loc[b], loc[c] = [a, 0], [a, 1]
for _ in range(m):
op = list(map(int, input().split()))
if op[0] == 1:
swap(op[1], op[2])
else:
cur = op[1]
while tree[cur][0] != -1:
cur = tree[cur][0]
print(cur)OOP方式。同一个parent要特殊考虑。否则同一个 parent,48行相当于又交换。
python
class TreeNode:
def __init__(self, val):
self.val = val
self.left = None
self.right = None
self.parent = None
class BinaryTree:
def __init__(self, n):
self.root = TreeNode(0)
self.node_dict = {0: self.root}
self.build_tree(n)
def build_tree(self, n):
for _ in range(n):
idx, left, right = map(int, input().split())
if idx not in self.node_dict:
self.node_dict[idx] = TreeNode(idx)
node = self.node_dict[idx]
if left != -1:
if left not in self.node_dict:
self.node_dict[left] = TreeNode(left)
left_node = self.node_dict[left]
node.left = left_node
left_node.parent = node
if right != -1:
if right not in self.node_dict:
self.node_dict[right] = TreeNode(right)
right_node = self.node_dict[right]
node.right = right_node
right_node.parent = node
def swap_nodes(self, x, y):
node_x = self.node_dict[x]
node_y = self.node_dict[y]
px, py = node_x.parent, node_y.parent
if px == py:
px.left, px.right = px.right, px.left
return
# Swap in the parent's children references
if px.left == node_x:
px.left = node_y
else:
px.right = node_y
if py.left == node_y:
py.left = node_x
else:
py.right = node_x
# Swap their parent references
node_x.parent, node_y.parent = py, px
def find_leftmost_child(self, x):
node = self.node_dict[x]
while node.left:
node = node.left
return node.val
def main():
t = int(input())
for _ in range(t):
n, m = map(int, input().split())
tree = BinaryTree(n)
for _ in range(m):
op, *args = map(int, input().split())
if op == 1:
x, y = args
tree.swap_nodes(x, y)
elif op == 2:
x, = args
print(tree.find_leftmost_child(x))
if __name__ == "__main__":
main()思路:建树,注意交换节点的时候搞清楚哪个变量在引用什么,否则容易出现死循环之类的
python
# 夏天明 元培学院
class Node:
def __init__(self, name):
self.name = name
self.child = [None, None]
self.parent = None
def findLef(self):
curr = self
while (lef := nodes[curr.child[0]]):
curr = lef
return curr.name
for o in range(int(input())):
n, m = map(int, input().split())
nodes = [Node(i) for i in range(n)] + [None]
for o in range(n):
x, *idx = map(int, input().split())
nodes[x].child = idx
for i in [0,1]:
if idx[i] != -1:
nodes[idx[i]].parent = (nodes[x],i)
for o in range(m):
token, *idx = map(int, input().split())
if token == 1:
p = [nodes[i].parent for i in idx]
for i in [0,1]:
p[i][0].child[p[i][1]] = idx[1-i]
nodes[idx[i]].parent = p[1-i]
else:
print(nodes[idx[0]].findLef())思路:没有特别的操作。20min。
python
# 谭琳诗倩、2200013722
class BinaryTree:
def __init__(self,root):
self.root = root
self.left = None
self.right = None
self.father = None
for _ in range(int(input())):
n,m = map(int,input().split())
tree_list = list(BinaryTree(i) for i in range(n))
for __ in range(n):
root,left,right = map(int,input().split())
if left != -1:
tree_list[root].left = tree_list[left]
tree_list[left].father = tree_list[root]
if right != -1:
tree_list[root].right = tree_list[right]
tree_list[right].father = tree_list[root]
for __ in range(m):
type,*tu = map(int,input().split())
if type == 1: # swap
x,y = tu
tree1,tree2 = tree_list[x],tree_list[y]
father1 = tree1.father
father2 = tree2.father
if father2 is father1:
father2.left,father2.right = father2.right,father2.left
else:
if father1.left == tree1:
father1.left = tree2
else: father1.right = tree2
if father2.left == tree2:
father2.left = tree1
else: father2.right = tree1
tree1.father,tree2.father = father2,father1
elif type == 2:
node = tree_list[tu[0]]
while node.left:
node = node.left
print(node.root)python
# 23n2300011072(X) 蒋子轩
class TreeNode:
def __init__(self,val=0):
self.val=val
self.left=None
self.right=None
def build_tree(nodes_info):
nodes=[TreeNode(i) for i in range(n)]
for val,left,right in nodes_info:
if left!=-1:
nodes[val].left=nodes[left]
if right!=-1:
nodes[val].right=nodes[right]
return nodes
def swap_nodes(nodes,x,y):
for node in nodes:
if node.left and node.left.val in[x,y]:
node.left=nodes[y] if node.left.val==x else nodes[x]
if node.right and node.right.val in[x,y]:
node.right=nodes[y] if node.right.val==x else nodes[x]
def find_leftmost(node):
while node and node.left:
node=node.left
return node.val if node else -1
for _ in range(int(input())):
n,m=map(int,input().split())
nodes_info=[tuple(map(int,input().split())) for _ in range(n)]
ops=[tuple(map(int,input().split())) for _ in range(m)]
nodes=build_tree(nodes_info)
for op in ops:
if op[0]==1:
swap_nodes(nodes,op[1],op[2])
elif op[0]==2:
print(find_leftmost(nodes[op[1]]))思路:只记录父子关系即可
python
# Xinjie Song, Phy
for _ in range(int(input())):
n, m = map(int, input().split())
edges = {i: [0, 0, 0] for i in range(n)}
for i in range(n):
x, y, z = map(int, input().split())
edges[x][1], edges[x][2] = y, z
if y != -1:
edges[y][0] = x
if z != -1:
edges[z][0] = x
for __ in range(m):
s = list(map(int, input().split()))
if s[0] == 1:
x, y = s[1], s[2]
x_father, y_father = edges[x][0], edges[y][0]
x_idx, y_idx = 1 + (edges[x_father][2] == x), 1 + (edges[y_father][2] == y)
edges[x_father][x_idx], edges[y_father][y_idx], edges[x][0], edges[y][0] = y, x, y_father, x_father
else:
x = s[1]
while edges[x][1] != -1:
x = edges[x][1]
print(x)