门牌制作

代码如下:
python
num = 0
for i in range(1, 2021):
num += str(i).count('2')
print(num)
特别数的和

代码如下:
python
n = int(input())
ans = 0
for i in range(1, n + 1):
if '2' in str(i) or '0' in str(i) or '1' in str(i) or '9' in str(i):
ans += i
print(ans)
成绩统计


代码如下:
python
n = int(input())
num = []
for _ in range(n):
num.append(int(input()))
ok, well = 0, 0
for x in num:
if x >= 85:
well += 1
if x >= 60:
ok += 1
ans1 = (ok / n) * 100
ans2 = (well / n) * 100
print("{:.0f}%".format(ans1))
print("{:.0f}%".format(ans2))
冰雹数


代码如下:
python
n = int(input())
max_value = 0 # 记录所有数字变换过程中的最大值
# 遍历从1到n的所有数字
for i in range(1, n + 1):
num = i
# 更新当前数字本身(它也是序列的一部分)
if num > max_value:
max_value = num
# 进行冰雹变换
while num != 1:
if num % 2 == 0:
num //= 2
else:
num = num * 3 + 1
# 更新最大值
if num > max_value:
max_value = num
print(max_value)
饮料换购

代码如下:
python
n = int(input())
ans = n
while n >= 3:
ans += n // 3
n = n % 3 + n // 3
print(ans)
三角回文数

代码如下:
python
def is_palindrome(n):
s = str(n)
return s == s[::-1]
def is_triangular(n):
# 解 k^2 + k - 2n = 0
# 判别式 D = 1 + 8n
D = 1 + 8 * n
root = int(D ** 0.5)
return root * root == D and (root - 1) % 2 == 0
n = 20220514
while True:
if is_triangular(n) and is_palindrome(n):
print(n)
break
n += 1
递增三元组


二分查找:bisect库
ls = 所查找的数组,x = 需要查找的值
index1 = bisect.bisect(ls, x) index2 = bisect.bisect_left(ls, x) index3 = bisect.bisec_right(ls, x)
注意:bisect.biscet(ls, x) == bisect.bisect_right(ls, x)
1.所查找的数组中无元素 x,返回 x 在 ls 中的"插入点索引,且保持数组有序"。
python
import bisect
ls = [1,5,9,13,17]
index1 = bisect.bisect(ls,7)
index2 = bisect.bisect_left(ls,7)
index3 = bisect.bisect_right(ls,7)
print("index1 = {}, index2 = {}, index3 = {}".format(index1, index2, index3))
# index1 = 2, index2 = 2, index3 = 2
2.所查找的数组中只有一个元素 x,bisect_left 返回对应的索引,bisect_right 返回对应的索引 +1。
python
import bisect
ls = [1,5,9,13,17]
index1 = bisect.bisect(ls,9)
index2 = bisect.bisect_left(ls,9)
index3 = bisect.bisect_right(ls,9)
print("index1 = {}, index2 = {}, index3 = {}".format(index1, index2, index3))
# index1 = 3, index2 = 2, index3 = 3
3.所查找数组中有多个 x,bisect_left 返回最左边的索引,bisect_right 返回最右边的索引 +1。
python
import bisect
ls = [1,5,5,5,17]
index1 = bisect.bisect(ls,5)
index2 = bisect.bisect_left(ls,5)
index3 = bisect.bisect_right(ls,5)
print("index1 = {}, index2 = {}, index3 = {}".format(index1, index2, index3))
# index1 = 4, index2 = 1, index3 = 4
思路:
测试样例:
A[i] :1 3 5 7 9
B[j] : 3 5 7 9 11
C[k]: 5 7 9 11 13
结果:
a = bisect.bisect_left(A, B[j]) = 3
c = n - bisect.bisect_right(C, B[j]) =5- 2 = 3
由此找出A中<7的数的数量,和C中>7的数的数量。
同理:当B[j]=8时,因为8不在A与C中,a与c是在A与C中"合适的插入点索引,使得数组有序"。
所以a=4,c=5-2=3。
代码如下:
python
import bisect
n = int(input())
A = list(map(int, input().split()))
B = list(map(int, input().split()))
C = list(map(int, input().split()))
A.sort()
B.sort()
C.sort()
ans = 0
for j in range(n):
a = bisect.bisect_left(A, B[j])
c = (n - bisect.bisect_right(C, B[j]))
ans += a * c
print(ans)
连号区间数


在没有重复元素的情况下,连号区间等价于:区间内最大值-最小值==区间长度-1
代码如下:
python
n = int(input())
a = list(map(int, input().split()))
ans = 0
for i in range(n):
max_num = float('-inf')
min_num = float('inf')
for j in range(i, n):
max_num = max(max_num, a[j])
min_num = min(min_num, a[j])
if max_num - min_num == j - i:
ans += 1
print(ans)
螺旋矩阵

代码如下:
python
n, m = map(int, input().split())
r, c = map(int, input().split())
a = [[0] * m for _ in range(n)]
x, y = 0, 0
value = 1
a[x][y] = value
while value < n * m:
#向右
while y + 1 < m and a[x][y + 1] == 0:
value += 1
y += 1
a[x][y] = value
#向下
while x + 1 < n and a[x + 1][y] == 0:
value += 1
x += 1
a[x][y] = value
#向左
while y - 1 >= 0 and a[x][y - 1] == 0:
value += 1
y -= 1
a[x][y] = value
#向上
while x - 1 >= 0 and a[x - 1][y] == 0:
value += 1
x -= 1
a[x][y] = value
print(a[r - 1][c - 1])
图像模糊


代码如下:
python
n, m = map(int, input().split())
a = []
for _ in range(n):
a.append(list(map(int, input().split())))
b = [[0] * m for i in range(n)]
dic = [(0, 0), (0, -1), (-1, -1), (-1, 0), (-1, 1), (0, 1), (1, 1), (1, 0), (1, -1)]
for i in range(n):
for j in range(m):
sum_num = 0
num = 0
for k in range(9):
x, y = i + dic[k][0], j + dic[k][1]
if 0 <= x < n and 0 <= y < m:
sum_num += a[x][y]
num += 1
b[i][j] = sum_num // num
for i in range(n):
print(' '.join(map(str, b[i])))
打印大X


代码如下:
python
m, n = map(int, input().split())
lst = [["."] * (m + n - 1) for _ in range(n + 1)]
for i in range(n):
for j in range(m):
#副对角线
lst[i][i + j] = '*'
#正对角线
lst[i][m + n - 2 - i - j] = '*'
for i in range(n):
print(''.join(lst[i]))
等差素数列

代码如下:
我自己写的代码(能跑出来答案但是不太规范)
python
import math
def sus(n):
for i in range(2, int(math.sqrt(n)) + 1):
if n % i == 0:
return False
return True
for i in range(2, 10000):
if sus(i):
for k in range(1, 500):
a = [0] * 10
a[0] = i
for j in range(9):
if sus(a[j] + k):
a[j + 1] = a[j] + k
else:
break
if a[9] != 0:
print(k)
标准代码:
python
import math
def is_prime(n):
if n < 2:
return False
for i in range(2, int(math.sqrt(n)) + 1):
if n % i == 0:
return False
return True
# 添加一个标志位
found = False
# 搜索长度为10的等差素数数列
for start in range(2, 10000): # 起始素数
if found: # 如果已经找到,跳出外层循环
break
if is_prime(start):
for diff in range(1, 500): # 公差
# 检查是否能构成长度为10的等差数列
is_valid = True
for j in range(1, 10): # 只需要检查后续9个数
if not is_prime(start + j * diff):
is_valid = False
break
# 如果找到了,输出结果并设置标志位
if is_valid:
print(diff)
found = True # 设置标志位
break # 跳出内层循环
分巧克力


代码如下:
python
n, k = map(int, input().split())
a = []
for i in range(n):
h, w = map(int, input().split())
a.append((h, w))
def check(x):
cnt = 0
for h, w in a:
cnt += (h // x) * (w // x)
if cnt >= k:
return True
else:
return False
left, right = 1, 100000
ans = 1
while left <= right:
mid = (left + right) // 2
if check(mid):
ans = mid
left = mid + 1
else:
right = mid - 1
print(ans)
航班时间



思路:时差可以被消掉 ,例如我们假设a,b两地的时差为t 当飞机在a地 t1 时刻起飞此时b地的时间为t1+t 我们假设需要经过B时间飞机能从a->b则飞机到b地的时间为 t1+t+B ,题目给力我们飞机到b地的时间是t2则 t2=t1+t+b ,同样我们可以推导出 t3-t+B=t4 其中t3是飞机从b地起飞的时间t4是飞机到a地的时间 ,两者相加就把时差t给消掉了
python
#将时间t换算成秒
def transfer(t):
#也就是时间后面有括号,即跨天
if len(t.split()) > 1:
t1, t2 = t.split()#t1是正常时间,t2是(+1)
t2 = int(t2[2]) * 24 * 3600#t2[2]就是括号里的数字
t1 = transfer(t1)
return t1 + t2
else:
t = t.split(":")
return int(t[0]) * 3600 + int(t[1]) * 60 + int(t[2])
n = int(input())
for _ in range(n):
#maxsplit旨在只算前面的两个正常时间
t1, t2 = input().split(maxsplit = 1)
t3, t4 = input().split(maxsplit = 1)
t = (transfer(t2) + transfer(t4) - transfer(t1) -transfer(t3)) // 2
hour = t // 3600
minute = t % 3600 // 60
second = t % 3600 % 60
print("%02d:%02d:%02d" % (hour, minute, second))
移动距离

代码如下:
python
import math
#计算扇形半径
r = math.sqrt(233 ** 2 + 666 ** 2)
#计算扇形弧度
hu = math.atan(666 / 233)
#弧长 = 半径 * 弧度
l = hu * r
print(round(l + r))
移动距离


python
w, m, n = map(int, input().split())
def get_position(num):
# 行号(0-based)
row = (num - 1) // w
# 列号(0-based)
if row % 2 == 0: # 偶数行,从左到右
col = (num - 1) % w
else: # 奇数行,从右到左
col = w - 1 - (num - 1) % w
return row, col
# 获取m和n的坐标
row_m, col_m = get_position(m)
row_n, col_n = get_position(n)
# 计算曼哈顿距离
distance = abs(row_m - row_n) + abs(col_m - col_n)
print(distance)
蚂蚁感冒


关键观察:
蚂蚁碰头后掉头,相当于它们互相穿过但交换身份(包括感冒状态)。
所以本质上可以认为蚂蚁保持原方向不变,只是穿过时交换了"标签"。
那么感冒传播就变成了:感冒蚂蚁在原方向上走,所有与它方向相对、且在它前进路径上会相遇的蚂蚁都会被感染。
两种情况(以第一只蚂蚁方向分):
- 第一只蚂蚁向右(正数):
· 它在它右边且向左走的蚂蚁,一定会被它感染(因为它们相向而行)。
· 然后这些被感染的蚂蚁中,如果它们在原第一只蚂蚁的左边且向右走,这些也会被感染(因为它们和被感染的蚂蚁相向而行)。
· 所以计算方法是:
· 右边向左的蚂蚁数 = right_to_left
· 左边向右的蚂蚁数 = left_to_right
· 总感冒数 = 1 + right_to_left + (如果 right_to_left > 0 则加 left_to_right 否则不加)
- 第一只蚂蚁向左(负数):
· 它在它左边且向右走的蚂蚁,一定会被感染。
· 然后这些被感染的蚂蚁中,如果它们在原第一只蚂蚁的右边且向左走,也会被感染。
· 所以计算方法是:
· 左边向右的蚂蚁数 = left_to_right
· 右边向左的蚂蚁数 = right_to_left
· 总感冒数 = 1 + left_to_right + (如果 left_to_right > 0 则加 right_to_left 否则不加)
代码如下:
python
n = int(input())
ants = list(map(int, input().split()))
first = ants[0]
ans = 0
left_to_right = 0
right_to_left = 0
for ant in ants[1:]:
if ant < 0 and abs(ant) > abs(first):
right_to_left += 1
elif ant > 0 and abs(ant) < abs(first):
left_to_right += 1
if first > 0:
if right_to_left > 0:
ans = 1 + right_to_left + left_to_right
else:
ans = 1
else:
if left_to_right > 0:
ans = 1 + left_to_right + right_to_left
else:
ans = 1
print(ans)