定义两数 a b 如果 a 的最后一位移到第一位一直移移到后面能形成b, 那么 a 是 b cyclic shift.
给定一个数组A, 如果A[i]是A[j]的cyclic shift并且 i < j那么 A[i] A[j]就是 cyclic shift pair.求这个数组一共有多少个cyclic shift pair. (456 的所有 cyclic shift 是:645, 564)
解法一: 暴力
遍历所有的对, 判断这一对数是不是cyclic shift, 如果是就res++, 如果不是就continue 但是会超时
解法二: 线性查找
如果我们遇到了一个数, 我们可以把这个数存到map, 前提是map里所有的数都不是这个数的cyclic shift. map的key是这个数的str然后 value是这个数和这个数的cyclic shift出现的次数。同时把更新后的value累加到res里。 例如 [13, 5604, 31, 2, 13, 4560]
我们遇到 13, 把13放进字典. {13:1} res = 0
遇到5604, 没有5604的shift在字典里, 更新map. {13:1, 5604:1} res = 0
遇到31, 发现13是31 shift, 更新map. {13:1+1,5604:1} res = 0+1 = 1
遇到2, 没有发现shift, 更新map {13:2,5604:1,2:1} res = 1
遇到13, 发现shift, 更新map {13:2+1, 5604:1,2:1} res = 1+2 = 3
遇到4560, 发现shift, 更新map, {13:3, 5604:1+1, 2:1} res = 3+1 = 4
因为这题每个数取值在 , 所以每次发现shift时间是常数, 遍历n次总共需要 时间
python代码:
def sol(a):
res = [0]
dic = {}
def check(s):
s = str(s)
for i in range(len(s)):
s = s[-1]+s[:-1]
if s in dic:
res[0]+=dic[s]
dic[s] +=1
return
dic[s] = 1
return
for n in a:
check(n)
return res[0]