一、总体情况
得分:25+0+25+25=75(排名第5)
二、题目分析
第一题:合并序列
题目
分析
较为容易,用 for
循环一次检验每个序列即可。(这里的 python
实现用到了数组切片)
代码
class Solution:
def __init__(self) -> None:
pass
def solution(self, N, arr, T):
result = []
l = len(T)
for i in range(len(arr)):
if len(arr[i])>=l and arr[i][:l]==T:
result.append(arr[i])
return result
if __name__ == "__main__":
N = int(input().strip())
arr = []
for i in range(N):
arr.append(input().strip())
T = input().strip()
sol = Solution()
result = sol.solution(N, arr, T)
result.sort()
print("\n".join(result))
第二题:千问万问
题目
分析
根据 优快云 往届竞赛经验,数据范围一般不会很大,所以暴力枚举不失为本题的一个方案。当然,如果追求效率,可以采用二分搜索的方法。但由于时间考量,笔者选择枚举。(本题数据有锅,因此未得分)
代码
class Solution:
def __init__(self) -> None:
pass
def solution(self, n, q, nums, arr):
result = []
for i in range(q):
cnt = 0
for j in nums:
if j>=arr[i][0] and j<=arr[i][1]:
cnt = cnt+1
result.append(cnt)
return result
if __name__ == "__main__":
arr_temp = [int(item) for item in input().strip().split()]
n = int(arr_temp[0])
q = int(arr_temp[1])
nums = [int(item) for item in input().strip().split()]
arr = []
for i in range(q):
arr.append([int(item) for item in input().strip().split()])
sol = Solution()
result = sol.solution(n, q, nums, arr)
for i in range(len(result)):
print(result[i])
第三题:连续子数组的最大和
题目
分析
动态规划几乎是每一届 优快云 竞赛的必考点,这次也不例外(虽然此题十分基础)。我们用 d p [ i ] \mathrm{dp}[i] dp[i] 表示以 i i i 号索引结尾的有着最大和的连续子数组。则:
- 显然有 d p [ 0 ] = n u m s [ 0 ] \mathrm{dp}[0]=\mathrm{nums}[0] dp[0]=nums[0].
- 从前往后维护 { d p [ i ] } \mathrm{\{dp[i]\}} {dp[i]} 数组:假如 d p [ i − 1 ] \mathrm{dp}[i-1] dp[i−1] 已确定,则对于 d p [ i ] \mathrm{dp}[i] dp[i], 它要么包含 n u m s [ i − 1 ] \mathrm{nums}[i-1] nums[i−1], 要么只有 n u m s [ i ] \mathrm{nums}[i] nums[i] 一项, 二者取最大并不要忘记追踪最大值即可.
根据以上思路,
代码
class Solution:
def __init__(self) -> None:
pass
def solution(self, n, arr):
dp = [0 for _ in range(n)]
dp[0] = maxi = arr[0]
for i in range(1, n):
dp[i] = max(dp[i-1], 0)+arr[i]
maxi = max(maxi, dp[i])
return maxi
if __name__ == "__main__":
n = int(input().strip())
arr = [int(item) for item in input().strip().split()]
sol = Solution()
result = sol.solution(n, arr)
print(result)
第四题:降水量
题目
分析
这题如果从整体考虑其实很复杂, 但假如单看每一个 x x x 坐标单元格的情况, 那么其实一目了然: 第 i i i 号位置的 “水面” 位置是以下两个数值中的较高者:
- 包含 i i i 号位置的向左数最高的单元格和包含 i i i 号位置的向右数最高的单元格的较矮者.
- 地平线, 即 0 0 0. (这只是因为题目要求)
值得注意的是, 这里只要稍微多写一些代码就能做到优化: 运用动态规划的方式维护上述所谓 “包含 i i i 号位置的向左 (右) 数最高的单元格” 的数值. 因此代码如下:
代码
class Solution:
def __init__(self) -> None:
pass
def solution(self, n, arr):
result = 0
incleftmax = [arr[0]]+[0 for i in range(n-1)]
incrightmax = [0 for i in range(n-1)]+[arr[n-1]]
for i in range(1, n):
incleftmax[i] = max(incleftmax[i-1], arr[i])
for i in range(n-2, -1, -1):
incrightmax[i] = max(incrightmax[i+1], arr[i])
for i in range(n):
result = result+max(min(incleftmax[i], incrightmax[i]), 0)-arr[i]
return result
if __name__ == "__main__":
n = int(input().strip())
arr = [int(item) for item in input().strip().split()]
sol = Solution()
result = sol.solution(n, arr)
print(result)
三、写在最后:对 优快云 竞赛的一些建议
- 仍然希望 优快云 在赛后能第一时间发布官方题解, 以供参考学习.
- 希望 优快云 在之后的比赛中尽可能不出现数据出锅的问题, 即使有问题, 赛后也能对有争议的数据进行及时查验反馈, 并以此为据重新判分, 以鼓励选手集思广益.
- 题目描述过分简略和不清晰仍是一大问题, 对题面描述, 数据范围, 样例分析等没有看到形式上的改进.