问题解析
题目要求
给定射击点的坐标 (x,y),靶心位于 (0,0)。靶由同心圆构成,每个环的半径依次增加 1,中心环(半径为 1)得分最高,为 10,依次向外环得分递减 1。若点超出最外层环(半径为 10),得分为 0。
评分规则
如果点落在某个半径 ii 的圆内,得分为 11−i; 若点的欧几里得距离大于 10,得分为 0。
目标
通过计算点到靶心的欧几里得距离,判断点在哪个环中,从而确定分数。
解题思路
1. 计算距离
使用欧几里得距离公式: 距离= sqrt(x^2 + y^2) 这是点与圆心的直线距离,用于判断点与各个圆的关系。
计算欧几里得距离,why
在这道题中,我们需要根据射击点与靶心的距离判断得分,而欧几里得距离是最直观、符合物理意义的距离度量方式,能够准确表示点与靶心之间的直线距离。
1. 圆的几何特性
靶是由同心圆构成的,每个环的半径 r 是判断分数的关键参数。 圆的几何性质规定:点与圆心的距离小于圆的半径时,点在圆内。
欧几里得距离公式:
距离=sqrt((x - x0)^2 + (y - y0)^2)
对于此题,靶心的坐标是 (0,0),距离简化为:
距离=sqrt(x^2 + y^2)
通过计算射击点到靶心的欧几里得距离,可以直接比较这个距离与每个圆的半径,快速判断射击点属于哪个环。
2. 其他距离度量方式的局限性
如果不使用欧几里得距离,其他方式可能会出现问题:
-
曼哈顿距离: 曼哈顿距离是基于网格的度量方式,计算公式为:
距离=∣x−x0∣+∣y−y0∣
这种方式在计算方形或网格区域时有效,但在圆形区域中无法准确反映点与圆心的关系。
故欧几里得距离是圆形靶这种场景下的最适合度量方法
采用欧几里得距离:
直接反映点与圆心的几何关系。
符合题目和现实中的得分规则。
计算效率高且实现简单。
2. 判断环位置
按环半径从 1 到 10 遍历。 若计算出的距离小于当前环的半径,说明点在该环内,立即返回得分 11−环编号i。
3. 超出所有环
如果点的距离大于 10,即点不在任何环内,返回得分 0。
关键代码解析
import math
- 导入
math模块,使用平方根函数math.sqrt()计算欧几里得距离。
distance = math.sqrt(x ** 2 + y ** 2)
- 使用欧几里得公式计算点与靶心的距离。
for i in range(1, 11): # 环编号从1到10
if distance < i:
return 11 - i
- 从第一个环(半径为 1)开始,依次判断距离是否小于环的半径。
- 若满足条件,直接返回得分 11−环编号i。
- 提前结束遍历,保证效率。
return 0
- 当遍历完所有环后,若距离依然大于 10,说明点在靶外,返回 0。
注意点
1. 边界条件
若点刚好落在某个环的边界(如 距离=a),根据题意得分按在半径为a的环处理,故代码中采用 "<=" 判断。
2. 输入范围
- x , y 的值可能较大,但只需计算其平方和后开方
完整代码
import math
def solution(x: int, y: int) -> int:
# 计算点到靶心的欧几里得距离
distance = math.sqrt(x ** 2 + y ** 2)
# 判断得分
for i in range(1, 11): # 环编号从1到10
if distance < i:
return 11 - i
# 超出所有环,得分为0
return 0
if __name__ == '__main__':
# 测试样例
print(solution(1, 0) == 10)
print(solution(1, 1) == 9)
print(solution(0, 5) == 6)
print(solution(3, 4) == 6)
总结
- 时间复杂度:O(1)(因为最多遍历 10 个环,常数时间)。
- 空间复杂度:O(1)(只需存储距离和环编号)。