思路是把nums1和nums2中每个节点都当作一遍起点但是这样会重复,导致复杂度过高
暴力超时
def findLength(self, nums1, nums2):
"""
:type nums1: List[int]
:type nums2: List[int]
:rtype: int
"""
m_max = 0
for i in range(len(nums1)):
for j in range(len(nums2)):
k = 0
while i + k <len(nums1) and j + k <len(nums2) and nums1[i+k] == nums2[j+k]:
k += 1
m_max = max(k,m_max)
return m_max
采用改进的思路是将这两个字符串逐位进行对齐,这样的话就可以把两个字符串同时进行遍历
def findLength(self, nums1, nums2):
"""
:type nums1: List[int]
:type nums2: List[int]
:rtype: int
"""
def comp_max(Addm,Addn,length):
count,max_l = 0,0
for i in range(length):
if nums1[Addm+i] == nums2[Addn+i]:
count += 1
max_l = max(count,max_l)
else:
count = 0
return max_l
n = len(nums1)
m = len(nums2)
res = 0
for i in range(n): #相当于m不动,n向前移动
length = min(n-i,m)
res = max(res,comp_max(i,0,length))
for j in range(m): #相当于n不动,m向前移动
length = min(m-j,n)
res = max(res,comp_max(0,j,length))
return res
思路二分查找寻找长度
check里通过将子数组转为哈希值判断是否重复
注意用一个大的mod减少碰撞
def findLength(self, nums1, nums2):
"""
:type nums1: List[int]
:type nums2: List[int]
:rtype: int
"""
def check(m,nums1,nums2):
number1 = 0
number2 = 0
base = 113
mod = 10**9+1777
l = 0
rem = pow(base,m-1,mod)
record = set()
for i in range(m-1):
number1 = number1 *base + nums1[i]
for r in range(m-1,len(nums1)):
number1 = (number1 *base + nums1[r])%mod
record.add(number1)
number1 = (number1 - nums1[l]*rem)%mod
l += 1
l = 0
for i in range(m-1):
number2 = number2 *base + nums2[i]
for r in range(m-1,len(nums2)):
number2 = (number2 *base + nums2[r])%mod
if number2 in record:
return True
number2 = (number2 - nums2[l]*rem)%mod
l += 1
return False
l = 1
ans = 0
r = len(nums1)
while l <= r:
m = l + (r-l)//2
if check(m,nums1,nums2):
ans = m
l = m +1
else:
r = m-1
return ans