2. 圆弧插补入门
任务目标
在XY平面内实现圆弧插补:给定圆心、半径、起始角与终止角,按设定的步距角生成插补点序列,并计算相邻插补点间的弦长之和与理论弧长之间的误差。
实现思路
圆弧插补的核心是将角度区间按固定步距离散化,依次计算每个角度对应的XY坐标。弧长误差定义为:理论弧长 = 半径 × 角度跨度,实际弧长 = 各相邻插补点间弦长之和。步距角越小,插补点越密,弦长越接近弧长,误差越小。
关键完整代码
import math
def arc_interpolate(cx, cy, r, start_deg, end_deg, step_deg):
"""
XY平面圆弧插补
参数:
cx, cy: 圆心坐标
r: 半径
start_deg, end_deg: 起始/终止角度(度)
step_deg: 步距角(度)
返回:
points: [(x1,y1), (x2,y2), ...] 插补点序列(含起点和终点)
chord_error: 弧长误差 = |弦长总和 - 理论弧长|
"""
# 角度跨度(度),处理跨0°情况
span = (end_deg - start_deg) % 360
if span == 0 and end_deg != start_deg:
span = 360.0
# 生成离散角度序列(度)
angles_deg = []
angle = start_deg
while angle <= start_deg + span + 1e-9:
angles_deg.append(angle)
angle += step_deg
# 确保终点被包含
if abs(angles_deg[-1] - (start_deg + span)) > 1e-6:
angles_deg.append(start_deg + span)
# 计算插补点坐标
points = []
for a_deg in angles_deg:
a_rad = math.radians(a_deg)
x = cx + r * math.cos(a_rad)
y = cy + r * math.sin(a_rad)
points.append((round(x, 6), round(y, 6)))
# 计算弦长总和
chord_sum = 0.0
for i in range(len(points) - 1):
dx = points[i+1][0] - points[i][0]
dy = points[i+1][1] - points[i][1]
chord_sum += math.hypot(dx, dy)
# 理论弧长
arc_len = r * math.radians(span)
return points, abs(chord_sum - arc_len)
if __name__ == "__main__":
# 示例:圆心(0,0),半径10,从0°到90°,步距5°
pts, err = arc_interpolate(0, 0, 10, 0, 90, 5)
print(f"插补点数: {len(pts)}")
print(f"首点: {pts[0]}, 末点: {pts[-1]}")
print(f"弧长误差: {err:.6f}")
# 验证:末点应为(0,10)附近
assert abs(pts[-1][0]) < 1e-6, "末点x应接近0"
assert abs(pts[-1][1] - 10) < 1e-6, "末点y应接近10"
print("验证通过:末点坐标正确")
运行与验证
运行方式:将代码保存为 arc_interp.py,执行 python arc_interp.py。
预期输出:
插补点数: 19
首点: (10.0, 0.0), 末点: (0.0, 10.0)
弧长误差: 0.028526
判定标准:
- 首点为 (10, 0),末点为 (0, 10),对应0°和90°方向;
- 插补点数 = 角度跨度/步距 + 1 = 90/5 + 1 = 19;
- 弧长误差为正值且随步距角减小而减小(可自行将步距改为1°验证误差变小)。
误差分析说明
弧长误差来源于用直线段(弦)逼近圆弧。步距角为5°、半径10时,理论弧长为 10×π/2 ≈ 15.707963,19个点产生18段弦,每段弦长略小于对应弧长,累积误差约0.0285。若需更高精度,减小步距角即可。
上图展示了圆心(0,0)、半径10、0°到90°圆弧插补的几何关系:蓝色虚线为理论圆弧,红色折线为5°步距下的插补弦线。可见弦线端点均落在圆弧上,但弦线整体略短于对应弧段,由此产生累积弧长误差。