Problem: An SNS has N users - User 1, User 2, \cdots, User N.  Between these N users, there are some relationships - M _friendships_ and K _blockships_.  For each i = 1, 2, \cdots, M, there is a bidirectional friendship between User A_i and User B_i.  For each i = 1, 2, \cdots, K, there is a bidirectional blockship between User C_i and User D_i.  We define User a to be a _friend candidate_ for User b when all of the following four conditions are satisfied:    * a \neq b.   * There is not a friendship between User a and User b.   * There is not a blockship between User a and User b.   * There exists a sequence c_0, c_1, c_2, \cdots, c_L consisting of integers between 1 and N (inclusive) such that c_0 = a, c_L = b, and there is a friendship between User c_i and c_{i+1} for each i = 0, 1, \cdots, L - 1.  For each user i = 1, 2, ... N, how many friend candidates does it have?

Submission attempts (in order):
class UnionFind:
    def __init__(self, N):
        self.rank = [0] * N
        self.parent = [i for i in range(N)]
        self.n = N
        self.size = [1 for i in range(N)]
    def find(self, x):
        if self.parent[x] == x:
            return x
        else:
            self.parent[x] = self.find(self.parent[x])
            return self.parent[x]
    def unite(self, x, y):
        x = self.find(x)
        y = self.find(y)
        if (x == y):
            return
        if (self.rank[x] < self.rank[y]):
            self.parent[x] = y
            self.size[y] += self.size[x]
        else:
            self.parent[y] = x
            self.size[x] += self.size[y]
            if self.rank[x] == self.rank[y]:
                self.rank[x] += 1
    def same(self, x, y):
        return self.find(x) == self.find(y)
    def get_parents(self):
        count = 0
        for i in range(self.n):
            if self.find(i) == i:
                count += 1
        return count
    def get_size(self, x):
        root = self.find(x)
        return self.size[root]
N,M,K = map(int,input().split())
U = UnionFind(N)
direct = [0 for i in range(N)]
for i in range(M):
    a,b = map(int,input().split())
    a,b = a-1,b-1
    U.unite(a,b)
    direct[a] += 1
    direct[b] += 1
neg = [0 for i in range(N)]
for i in range(K):
    c,d = map(int,input().split())
    c,d = c-1,d-1
    if U.same(c,d):
        neg[c] += 1
        neg[d] += 1
ans = []
for i in range(N):
    print(U.get_size(i))
    ans.append(U.get_size(i)-1-neg[i]-direct[i])
print(*ans)

class UnionFind:
    def __init__(self, N):
        self.rank = [0] * N
        self.parent = [i for i in range(N)]
        self.n = N
        self.size = [1 for i in range(N)]
    def find(self, x):
        if self.parent[x] == x:
            return x
        else:
            self.parent[x] = self.find(self.parent[x])
            return self.parent[x]
    def unite(self, x, y):
        x = self.find(x)
        y = self.find(y)
        if (x == y):
            return
        if (self.rank[x] < self.rank[y]):
            self.parent[x] = y
            self.size[y] += self.size[x]
        else:
            self.parent[y] = x
            self.size[x] += self.size[y]
            if self.rank[x] == self.rank[y]:
                self.rank[x] += 1
    def same(self, x, y):
        return self.find(x) == self.find(y)
    def get_parents(self):
        count = 0
        for i in range(self.n):
            if self.find(i) == i:
                count += 1
        return count
    def get_size(self, x):
        root = self.find(x)
        return self.size[root]
N,M,K = map(int,input().split())
U = UnionFind(N)
direct = [0 for i in range(N)]
for i in range(M):
    a,b = map(int,input().split())
    a,b = a-1,b-1
    U.unite(a,b)
    direct[a] += 1
    direct[b] += 1
neg = [0 for i in range(N)]
for i in range(K):
    c,d = map(int,input().split())
    c,d = c-1,d-1
    if U.same(c,d):
        neg[c] += 1
        neg[d] += 1
ans = []
for i in range(N):
    ans.append(U.get_size(i)-1-neg[i]-direct[i])
print(*ans)

Verdicts: Wrong Answer

Accepted