题目评价:前三题十分基础,第四题虽有一定思维难度,但相比传统的第四题仍有一些差距。当然,本次题解的重心也会放在第 4 题。
for
循环和 if
判断得出答案。python
中不能用简单的 round
(会自动省略 0
),而是使用更为规范的通配表达式 "{:.3f}".format()
来实现。#1
import math
class Solution:
def __init__(self) -> None:
pass
def solution(self, n, arr):
result = 0
sorted_arr = arr.sort()
for i in range(n-1, -1, -1):
if (n-1-i)%2==0:
result = result + math.pi*(arr[i]**2)
elif (n-1-i)%2==1:
result = result - math.pi*(arr[i]**2)
return "{:.3f}".format(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)
此题难度与第一题相近,均属于入门难度。我们只需要判断并维护最小值即可。
#2
class Solution:
def __init__(self) -> None:
pass
def solution(self, n, m, k, arr):
result = None
maxi = n+1
for i in range(n):
if arr[i]<=k and i!=m-1 and arr[i]!=0:
maxi = min(maxi, abs(i-m+1))
result = maxi
return result
if __name__ == "__main__":
arr_temp = [int(item) for item in input().strip().split()]
n = int(arr_temp[0])
m = int(arr_temp[1])
k = int(arr_temp[2])
arr = [int(item) for item in input().strip().split()]
sol = Solution()
result = sol.solution(n, m, k, arr)
print(result)
CSDN 竞赛为什么这么喜欢考 DP 啊……
这是一道 DP 经典问题 —— 背包问题。度娘上即有相应的解答,在此不再赘述。
#3
class Solution:
def __init__(self) -> None:
pass
def solution(self, n, M, vector):
result = None
dp = [0 for i in range(1100)]
for i in range(1, n+1):
for j in range(M, vector[i-1][0]-1, -1):
dp[j] = max(dp[j], dp[j-vector[i-1][0]]+vector[i-1][1])
result = dp[M]
return result
if __name__ == "__main__":
arr_temp = [int(item) for item in input().strip().split()]
n = int(arr_temp[0])
M = int(arr_temp[1])
vector = []
for i in range(n):
vector.append([int(item) for item in input().strip().split()])
sol = Solution()
result = sol.solution(n, M, vector)
print(result)
虽然已经有不少参赛者指出这是一道陈题(Codeforces 上面就有),但就题目本身而言,这题是本场比赛最有价值的一道题。这题的关键在于不要纠结于局部,而是注重整体。这也是许多看似复杂困难的问题的解法。我们通过追问的方式给出我的思考过程。
至此,我们已经可以给出一个数学化的表述:假设一个人的左舒适空间为 l i , 1 ≤ i ≤ N l_i, 1\leq i\leq N li,1≤i≤N, 右舒适空间为 r i , 1 ≤ i ≤ N r_i, 1\leq i\leq N ri,1≤i≤N, σ \sigma σ 为 { 1 , 2 , ⋯ , N } \{1, 2, \cdots, N\} {1,2,⋯,N} 上的任一置换, 则问题的一种局部解为 ∑ i = 1 n max { l i , r σ ( i ) } + N 加上一开始的 N 个人 ⏟ \sum\limits_{i=1}^{n}\max\{l_i, r_{\sigma(i)}\}+\underset{\underbrace{\text{加上一开始的 N 个人}}}{N} i=1∑nmax{li,rσ(i)}+ 加上一开始的 N 个人N。这里若 σ g ( i ) = i \sigma^{g}(i)=i σg(i)=i, 那么就成了一个圈( 1 ≤ g ≤ N 1\leq g\leq N 1≤g≤N),简单来说,这种状态一定能构造出来。
容易看出,为了使上式达到最小值,应该让大的和大的配,小的和小的配(直观上也很显然,严格的数学证明只要写一个 2 × N 2\times N 2×N 阵列去分析就行)。于是如果将 { l i } , { r i } \left\{ l_i \right\} ,\left\{ r_i \right\} {li},{ri} 排序为 r 1 ≥ r 2 ≥ ⋯ ≥ r N , l 1 ≥ l 2 ≥ ⋯ ≥ l N r_1\geq r_2\geq \cdots \geq r_N, l_1\geq l_2\geq \cdots \geq l_N r1≥r2≥⋯≥rN,l1≥l2≥⋯≥lN, 则所求的 N + min { ∑ i = 1 n max { l i , r σ ( i ) } } = N + ∑ i = 1 n max { l i , r i } N+\min\{\sum\limits_{i=1}^{n}\max\{l_i, r_{\sigma(i)}\}\} = N+\sum\limits_{i=1}^{n}\max\{l_i, r_i\} N+min{i=1∑nmax{li,rσ(i)}}=N+i=1∑nmax{li,ri}。剩下的代码是容易的。
class Solution:
def __init__(self) -> None:
pass
def solution(self, n, vector):
left = [vector[i][0] for i in range(n)]
right = [vector[i][1] for i in range(n)]
left.sort()
right.sort()
result = n
for i in range(n):
result = result + max(left[i], right[i])
return result
if __name__ == "__main__":
n = int(input().strip())
vector = []
for i in range(n):
vector.append([int(item) for item in input().strip().split()])
sol = Solution()
result = sol.solution(n, vector)
print(result)