(A、C、D、E、F、G题已得到洛谷的验证,答案全部正确。H题还没想明白,先暴力骗分)
(题(提)前声明:本人属于匕首(菜鸡~.~)水平,自己手写的题解,望各位佬批评指正,京津冀赛事延期,看看别的省的题)
A:攻击次数
n = 0
i = 1
while n < 2025:
if i & 1:
n += 15
else:
if i % 3 == 2:
n += 10
elif i % 3 == 0:
n += 7
else:
n += 5
i += 1
print(i - 1)
# print(181)
(这道题有歧义的地方为:三个英雄能否同时攻击,本题解考虑的为不能同时攻击)
挑攻击力大的技能使用即可,可见:奇数一定使用第二个英雄的技能,然后偶数情况的话模3余1用第一个英雄技能,其他情况用第三个英雄的技能。
B:最长字符串
(B题的文件没有找到,暂时省略,后期有的话补充。。。。)
C:LQ图形
w,h,v = MII()
t = h
b = w
for i in range(t):
print('Q' * w)
for i in range(b):
print('Q' * (v + w))
画图形的题,类似于画其他有规律的图形,观察可发现,可以将L分为上下两个部分,上面列数少的为h行,下面列数多的为w行,上下宽度分别为w和v+w。时间复杂度O(h + w)
D:最多次数
s = list(I())
n = len(s)
i = 0
res = 0
while i < n:
if s[i] in ['l','q','b']:
f = defaultdict(int)
j = 0
while j + i < n and j < 3:
f[s[j + i]] = 1
j += 1
if f['l'] == 1 and f['q'] == 1 and f['b'] == 1:
res += 1
i += 2
i += 1
print(res)
贪心:遇到连续的三个某个顺序的l,q,b,就把他拿掉。时间复杂度O(n)
E:A · B Problem
n = II()
f = [0] * (n + 2)
for i in range(1,n + 1):
for j in range(i,n + 1,i):
f[j] += 1
pre = [0] * (n + 2)
for i in range(1,n + 1):
pre[i] = pre[i - 1] + f[i]
res = 0
for i in range(1,n + 1):
res += f[i] * pre[n - i]
print(res)
优先找到所有L的因数的个数,然后求出所有因子的前缀和,(例如:6可以被分解为4个因数对(1,6),(2,3),(3,2),(6,1)),然后最后求的是相加为L的种类数,所以直接相乘即可。
时间复杂度:O(nlogn)
(计算因子的两层循环是调和级数,复杂度为O(nlogn),可以记一下。2^20大约是10^6)
(调和级数是这个样子:n*( +
+ .... +
),括号内这一部分可以用微积分求出为log级别)
F:园艺
n = II()
h = LII()
res = 1
for d in range(1,n):
di = (n + d - 1) // d
if di <= res:
break
for i in range(n):
tot = 1
prev = h[i]
cmx = 1
k = 1
while i + k * d < n:
cnt = h[i + k * d]
if cnt > prev:
tot += 1
cmx = max(cmx,tot)
else:
tot = 1
prev = cnt
k += 1
res = max(res,cmx)
print(res)
题目要求间隔相同,并且高度严格递增,所以这是一道等间隔最长上升子序列问题
第一层循环d是跳跃的步数,第二层循环是开始的元素位置,while循环是按照步数寻找等间隔的元素,tot是当前的最长序列长度,cmx是步数为d时的最长序列长度,prev是前一个元素的值。
时间复杂度:O(n²logn)(大致算了一下,n为5000时,大概为3*10^8,不过因为有早停策略,并且d越大就越早结束,实际情况到不了这么大,这里就不细算了,感兴趣的code友可以算算)
(第二个for+while循环又是调和级数的复杂度)
G:书架还原
n = II()
a = [0] + LII()
p = [0] * (n + 1)
res = 0
for i in range(1,n + 1):
p[a[i]] = i
for i in range(1,n + 1):
if a[i] != i:
p[a[i]] = p[i]
a[i],a[p[i]] = a[p[i]],a[i]
res += 1
print(res)
贪心,总处理次数为所有环的长度减一的和(判环可以用标记法进行判断,也是O(n))
时间复杂度:O(n)
H:异或和
这道题没写,想着暴力骗点分完事了,后来观察到a的数据范围只有2^20,大约10^6,而且题目中是求异或运算,所以一定和位运算有关系,大概要创建一个二维数组dp[n][21],然后进行计算。
(没写了,后边补吧。。。。)
时空复杂度应该都是:O(20 * n)