问题:
如图,让更多的人找到自己想要的位置。
思路:
递归剔除那些没有人想要坐的位置。
构造列表,M = [2,2,0,5,3,5,7,4]
M[2]
等于0,表示C被映射到了a上。
代码:
def naive_max_perm(M, A=None):
if A is None:
A = set(range(len(M)))
if len(A) == 1: return A
B = set(M[i] for i in A)
C = A - B
if C:
A.remove(C.pop())
return naive_max_perm(M,A)
return A
代码解析:
A:剩余人员的集合;
B:被指向座位的集合;
优化算法:
以上时间复杂度为$n^2$,可以使用一个计数列表替代B,如果该座位有人指向则+1,剔除没有人指向的座位即可。
代码:
def max_perm(M):
n = len(M)
A = set(range(n)) #所有座位
count = [0] #初始化所有指向
for i in M:
count[i] += 1
Q = [i for i in A if count[i] == 0] # 没人指向的座位的集合
# 剔除座位
while Q:
i = Q.pop()
A.remove(i)
j = M[i] #将该指向-1
count[j] -= 1
if count[j] == 0:
Q.append(j)
这样时间复杂度为线性级。