给定一个非负整数数组 A,如果该数组每对相邻元素之和是一个完全平方数,则称这一数组为正方形数组。
返回 A 的正方形排列的数目。两个排列 A1 和 A2 不同的充要条件是存在某个索引 i,使得 A1[i] != A2[i]。
示例 1:
输入:[1,17,8]
输出:2
解释:
[1,8,17] 和 [17,8,1] 都是有效的排列。
示例 2:
输入:[2,2,2]
输出:1
提示:
1 <= A.length <= 12
0 <= A[i] <= 1e9
方案一:
原理:迭代器遍历,超出时间限制。
import itertools
import math
class Solution:
def numSquarefulPerms(self, nums: List[int]) -> int:
if(len(nums) == 1):return 1
if(len(list(set(nums))) == 1):return 1 if(math.sqrt(nums[0]*2) == math.sqrt(nums[0] * 2 ) // 1) else 0
l = 0
temp = []
for num in itertools.permutations(nums):
if num in temp:
continue
temp.append(num)
for i in range(1,len(num)):
re = math.sqrt(num[i] + num[i-1])
if(re != re // 1):
break
else:
l += 1
return l
方案二:
原理:回溯
class Solution(object):
def numSquarefulPerms(self, A):
N = len(A)
count = collections.Counter(A)
graph = {x: [] for x in count}
for x in count:
for y in count:
if(math.sqrt(x+y) == math.sqrt(x+y) // 1):
graph[x].append(y)
def dfs(x, todo):
count[x] -= 1
if todo == 0:
ans = 1
else:
ans = 0
for y in graph[x]:
if count[y]:
ans += dfs(y, todo - 1)
count[x] += 1
return ans
return sum(dfs(x, len(A) - 1) for x in count)