1. 奇数倍数
题目描述
解析
直接看代码
代码
n = 2
while True:
X = 2019
X *= n
n += 1
lis = list(set(str(X)))
flag = True
for i in lis:
if int(i) % 2 == 0:
flag = False
break
if flag:
print(X)
break
2. 第几个幸运数字
题目描述
解析
注意3/5/7是因子(一开始没注意,看傻了)
代码
count = 0
for i in range(30):
for j in range(30):
for k in range(30):
if (7**i) * (5**j) * (3**k) <59084709587505:
count += 1
print(count+1)
2. 四平方和
题目描述
解析
首先说明没有AC,我只拿了87分😔,如果Python有什么能AC的还请大佬务必指点一下!
这个题听说有两种做法,一种二分一种是哈希表,所以就用python的字典实现哈希表的方法。(也许用二分就能AC也说不准哦,不过我没试就是了)
题目要求除了 **a ^2 + b ^2 + c ^2 + d ^2 == N**以外;还要求了输出时**a<=b<=c<=d**
先不看输出的要求,我们根据四方和公式可以知道,如果我们知道了c^2 + d^2 的和,也就知道了a^+c^2的和
根据上面,我们可以把代码分成两部分,cd一部分,ab一部分
首先是cd一部分,两层for循环cd(这里有个小技巧能保证c<d),在cd平方和不大于N的时候,将所有情况保存在字典里,其中key=c^2+d^2,value = (c,d)
然后是ab这一部分,也是两层for循环,在ab平方和不大于N的时候,用N减去ab的平方和,出来的就是cd的平方和,也就是key值,个人感觉就像是在取cd的交集,因为第一部分直接遍历求cd的平方和,第二部分用N减去ab的平方和求cd的平方和,找到相等的平方和就是我们要的了
那么关于比较大小怎么做呢?注意代码的for循环
代码
N = int(input())
table = {}
for c in range(0,int(N**0.5) + 1):
for d in range(c,int(N**0.5) + 1):
if c*c + d*d > N:
break
tem = int(c * c + d * d)
if not table.__contains__(tem):
table[tem] = [c,d]
def f(N):
for a in range(0,int(N**0.5) + 1):
for b in range(a,int(N**0.5) + 1):
if a*a + b*b > N:
break
cur = int(N - a * a - b * b)
if table.__contains__(cur):
print(f"{a} {b} {table[cur][0]} {table[cur][1]}")
return 0
f(N)
代码(超时)
# import math
#
# N = int(input())
# isfind = False
# edge = int(N ** 0.5)
# for a in range(edge):
# if isfind:
# break
# for b in range(a, edge):
# if isfind:
# break
# for c in range(b, edge):
# if N - a ** 2 - b ** 2 - c ** 2 >= 0:
# d = int(math.sqrt(N - a ** 2 - b ** 2 - c ** 2))
# if N == a ** 2 + b ** 2 + c ** 2 + d ** 2:
# isfind = True
# if c > d:
# c, d = d, c
# print(str(a) + " " + str(b) + " " + str(c) + " " + str(d))
# break
2. 迷宫
题目描述
解析
BFS!
代码
from collections import deque
graph = []
for i in range(30):
graph.append(list(map(int,input())))
# graph = [[0, 1, 0, 0, 0, 0],
# [0, 0, 0, 1, 0, 0],
# [0, 0, 1, 0, 0, 1],
# [1, 1, 0, 0, 0, 0]]
k = ('D', 'L', 'R', 'U') # 下,左,右,上
dir = [(1, 0), (0, -1), (0, 1), (-1, 0)]
vis = [[0] * 50 for i in range(30)] # 用来记录走过的坐标,走过标记为1
pre = [[""] * 50 for j in range(30)] # 用来记录当前坐标来源方式(DLRU)
def PrintPath(x, y): # 打印路线
if x == 0 and y == 0: # 如果到start位置就终止
return
if pre[x][y] == 'D': # 如果当前位置是下移得到的
PrintPath(x - 1, y) # 就向上移动
elif pre[x][y] == 'L': # 同理
PrintPath(x, y + 1)
elif pre[x][y] == 'R':
PrintPath(x, y - 1)
elif pre[x][y] == 'U':
PrintPath(x + 1, y)
print(pre[x][y], end="") # 输出【0,0】移动的第一个方式
def BFS(): # 三部分,走前准备,终止条件,走时记录。
# 走前准备:将队列que创造出来,默认start为初始位置,标记好走过,放在队列里
que = deque()
que.append((0, 0))
vis[0][0] = 1
# 开始走
while que:
# 终止条件
mov = que.popleft()
if mov[0] == 29 and mov[1] == 49:
PrintPath(29,49)
return
# 走时记录
for i in range(4):
nexttab = [0, 0] # 这里nexttab[0]表示下一个走的x坐标,nexttab[1]表示下一个点的y坐标,先往下走,每次for循环都回到初始点,然后换个方向走
nexttab[0] = mov[0] + dir[i][0]
nexttab[1] = mov[1] + dir[i][1]
# 经过两组洗礼,看看这个点是否能踩
if nexttab[0] < 0 or nexttab[0] > 29 or nexttab[1] < 0 or nexttab[1] > 49:
continue
if graph[nexttab[0]][nexttab[1]] == 1 or vis[nexttab[0]][nexttab[1]] == 1:
continue
# 洗礼过后可以踩,那么标记好
vis[nexttab[0]][nexttab[1]] = 1
que.append((nexttab[0], nexttab[1]))
pre[nexttab[0]][nexttab[1]] = k[i] # 标记时如何到这个点的,这样从end回到start才有方向
BFS()