这场比赛打的挺糟心的,之前在和朋友聊天,最后临时决定还是参加了这场比赛,然后从第一题开始就做的很不顺畅……
第一题最后舍弃了时间复杂度,选择了一个暴力方法进行求解,第二题是干脆看错了题目,把一个关键条件弄反了,结果硬生生把一道easy的题目做成了地狱难度,最后3分钟才猛然醒悟,但是已经没有时间做了,最后超时两分钟提交通过,真是要多不甘心有多不甘心。
然后最后一题也是,遇到了超时问题,始终没想到什么好的解决思路……
感觉就是诸事不顺,大概是因为前段时间和朋友聊天吹牛逼立下了flag的关系吧……
给出题目一的试题链接如下:
这题有一说一,做的不顺的最主要原因事实上还是看错题目的关系,题目的要求包括:
我最初的想法是先统计各个字符出现的次数,然后进行统计考察,但是遇到了困难,最后还是直接给出了最暴力的枚举法进行解答的,后续看看有没有更好的解题思路吧……
给出暴力求解的代码实现如下:
class Solution:
def longestNiceSubstring(self, s: str) -> str:
def is_nice(sub):
for c in sub:
if not c.lower() in sub or not c.upper() in sub:
return False
return True
n = len(s)
res = []
for i in range(n):
for j in range(n, i, -1):
if is_nice(s[i:j]):
res.append((s[i:j], i))
res = sorted(res, key=lambda x: (-len(x[0]), x[1]))
return "" if res == [] else res[0][0]
提交代码评测得到:耗时88ms,占用内存14.5MB。
看了一下当前的代码实现思路,貌似都是暴利求解的……
给出题目二的试题链接如下:
这道题其实只要注意匹配顺序必须与给定的groups
顺序一致,因此,我们只要采用贪婪匹配的方式进行子数组的注意匹配即可。
给出python代码实现如下:
class Solution:
def canChoose(self, groups: List[List[int]], nums: List[int]) -> bool:
n = len(groups)
flag = 0
i = 0
m = len(nums)
while i < m and flag < n:
if nums[i] != groups[flag][0]:
i += 1
continue
status = True
for j in range(len(groups[flag])):
if i+j >= m or nums[i+j] != groups[flag][j]:
status = False
break
if status:
i += len(groups[flag])
flag += 1
else:
i += 1
return flag == n
提交代码评测得到:耗时144ms,占用内存14.4MB。
当前最优的代码实现耗时72ms,但是看了一下,其核心算法思路是相同的,因此就不多做展开了。
给出题目三的试题链接如下:
这一题我的解题思路就是bfs,我们首先将最低点加入到队列当中,然后不断更新其邻接点上的高度,然后将邻接点顺序加入到队列当中,直到地图上所有的点全部都被赋予了高度。
我们给出python代码实现如下:
class Solution:
def highestPeak(self, isWater: List[List[int]]) -> List[List[int]]:
n, m = len(isWater), len(isWater[0])
q = []
res = [[-1 for _ in range(m)] for _ in range(n)]
for i in range(n):
for j in range(m):
if isWater[i][j] == 1:
res[i][j] = 0
q.append((i, j))
while q:
i, j = q.pop(0)
if i-1 >= 0 and res[i-1][j] == -1:
res[i-1][j] = res[i][j] + 1
q.append((i-1, j))
if i+1 < n and res[i+1][j] == -1:
res[i+1][j] = res[i][j] + 1
q.append((i+1, j))
if j-1 >= 0 and res[i][j-1] == -1:
res[i][j-1] = res[i][j] + 1
q.append((i, j-1))
if j+1 < m and res[i][j+1] == -1:
res[i][j+1] = res[i][j] + 1
q.append((i, j+1))
return res
提交代码评测得到:耗时5944ms,占用内存79.5MB。
当前的最优算法实现耗时4348ms,看了一下他们的算法实现,思路和我们是一致的,都是采用了bfs的思路,因此就不过多展开了,有兴趣的读者可以自行去看一下。
给出题目四的试题链接如下:
这一题比赛的时候遇到了超时问题,到最后也没有解决。赛后看了一下其他大佬们的解法,发现整体的思路在于使用了深度优先遍历,这个倒是没啥新奇的,不过最核心的优化点在于:
这样,就不需要记录整个树,而是只要维护1-50这些数向上的最近互质祖先位置即可。
但是他们的解法思路整体上来说确实看的半懂不懂的,就放在下面供读者参考了。
给出比赛中那些大佬们的解法如下:
class Solution:
def getCoprimes(self, nums: List[int], edges: List[List[int]]) -> List[int]:
n = len(nums)
graph = [[] for _ in range(n)]
for u, v in edges:
graph[u].append(v)
graph[v].append(u)
primes = [[j for j in range(1, 51) if gcd(i, j) == 1] for i in range(1, 51)]
current = [-1 for _ in range(51)]
ans = [-1 for _ in range(n)]
def dfs(x, parent):
nonlocal current
ans[x] = current[nums[x]]
current2 = current[:]
for j in primes[nums[x] - 1]:
current[j] = x
for v in graph[x]:
if v != parent:
dfs(v, x)
current[:] = current2
dfs(0, -1)
return ans
提交代码评测得到:耗时2412ms,占用内存135.8MB。