如何正确计算角度平均值?Python高尔夫游戏WASD角度输入反向问题
问题描述
我用Python开发一款高尔夫游戏,用Turtle库实现,核心涉及角度计算。原本让用户输入1-360°角度控制发球方向,现在改成WASD字符串输入方案:字符数量对应方向偏向程度,比如输入"wwa"时球朝北北西方向飞行。
但遇到一个问题:输入"wd"时,W对应360°(北)、D对应90°(东),直接取平均值得到225°,这和期望的东北方向完全相反。我的角度定义是北=360°、东=90°、南=180°、西=270°,这种跨0°(360°)的角度取平均总会出现反向问题。
当前实现代码:
ballinput = input("Angle: ") ballangle = 0 degreelist = [] #Each of the below statements appends the degrees for i in range(ballinput.count("w")): #to the degree list degreelist.append(360) for i in range(ballinput.count("a")): degreelist.append(270) for i in range(ballinput.count("s")): degreelist.append(180) for i in range(ballinput.count("d")): degreelist.append(90) for item in degreelist: ballangle += int(item) #which are added together so they can be ballangle /= len(ballinput) #averaged out into the final ball angle.
问题根源
角度是环形量(360°等价于0°),直接对角度数值取平均的逻辑不适用。比如360°(北)和90°(东),在环形角度里实际只相差90°,但数值上差270°,直接平均会取到两者的“反向中点”,导致方向完全相反。
解决方案
改用向量加权平均的方式:先把每个方向转换成直角坐标系下的单位向量,对所有输入对应的向量求和后,再将总向量转回角度。这样就能正确计算出加权后的方向。
修改后的代码:
import math ballinput = input("Angle: ") total_x = 0 total_y = 0 # 统计各方向对应的向量分量:东/西对应x轴,北/南对应y轴 total_x += ballinput.count("d") - ballinput.count("a") total_y += ballinput.count("w") - ballinput.count("s") # 处理无输入的情况,默认朝北 if total_x == 0 and total_y == 0: ballangle = 360 else: # 计算向量对应的弧度,再转成角度 radian = math.atan2(total_y, total_x) raw_angle = math.degrees(radian) # 转换为0-360°范围,并适配你的角度定义(北=360°、东=90°) ballangle = (raw_angle + 270) % 360 # 把0°替换为360°,符合定义习惯 if ballangle == 0: ballangle = 360 print(f"最终发球角度:{ballangle}°")
代码说明
- 向量计算逻辑:D(东)对应+x,A(西)对应-x;W(北)对应+y,S(南)对应-y。输入次数越多,对应分量的权重越大,能准确反映方向偏向。
- 角度适配:
math.atan2默认以东为0°、北为90°,通过+270再取模360,转换成以北为360°、东为90°的自定义角度体系。 - 输入"wd"时,总向量为(1,1),最终计算得到315°,对应北偏东45°的东北方向,完全符合预期。
内容的提问来源于stack exchange,提问作者topically
相关产品推荐
相关产品推荐

