我觉得吧,这道题, 比起算角度,数四边形才是应该关注的事。如果直接进行四重循环,每次从1度到179度,要进行179*179*179*179=1026625681次循环,1分钟之内算完是比较吃力的,此外还要查重。
所以,从减少循环下手。首先从四边形的四个角出发,选取其中最大的一个角(可与其他角并列最大),假定它是DCB。这个大角会唯一对应一个三角形DCB,再假定剩下的两个角中BDC是那个较小的(可并列最小),这样,循环时,应满足:
DCB >= CBA >= CBD+1
DCB >= CDA >= BDC+1
BDC <= CBD
这样,结合三角形内角和180度就得到了三角形CBD的循环条件:for DCB in range(61,180),for BDC in range(max(180-DCB-DCB+1,1),int((180-DCB)/2)+1)。
同样的,BDC的相邻角ADB,CBD的相邻角DBA也应满足相似的条件:
DCB >= CBA = CBD+DBA
DCB >= CDA = BDC+ADB
DCB >= DAB = 180-ADB-DBA
如此,可以从原来循环的10亿+下降到一千万+,测整数角神马的就是三角函数知识啦,只要一个小角CAD是整数,其他的拿180度减一减,就都是整数角啦。最后结果 132695,不到1分钟左右算完。import math
sind={}
cosd={}
for i in range(1,180):
sind[i] = math.sin(i/180*math.pi)
cosd[i] = math.cos(i/180*math.pi)
num=0
for DCB in range(61,180):
for BDC in range(max(180-DCB-DCB+1,1),int((180-DCB)/2)+1):
CBD=180-DCB-BDC
for ADB in range(1,DCB-BDC+1):
for DBA in range(max(1,180-ADB-DCB),min(DCB-CBD+1,180-ADB)):
BD = 1
AD = BD/sind[180-ADB-DBA]*sind[DBA]
DC = BD/sind[DCB]*sind[CBD]
AC = math.sqrt(AD*AD+DC*DC-2*AD*DC*cosd[ADB+BDC])
CAD = math.asin(min(sind[ADB+BDC]/AC*DC,1))/math.pi*180
if abs(CAD - round(CAD))<10**-9:
num+=1
print(num)
|