坐标变换方程代码验证及Numpy改写求助:结果不符排查
坐标变换函数问题排查与Numpy实现
问题描述
我编写了坐标变换函数transformation_coord,但运行结果与预期不符,需要验证方程编写是否正确,同时将这些方程改用Numpy实现。
原代码
import math def transformation_coord(x, y, l, r): """ :param x: x坐标 :param y: y坐标 :param l: 线段长度,默认值4 :param r: 圆弧半径,默认值3 :return: 变换后的坐标(x_trans, y_trans) """ x_trans = None y_trans = None # x变换方程 if x < 0: arccos_val = (r - y) / math.sqrt(((x - l) ** 2) + ((y - r) ** 2)) x_trans = (2 * l) + (r * math.pi) + (r * math.acos(arccos_val)) elif 0 <= x <= l and y < r: x_trans = x elif 0 <= x <= l and y >= r: x_trans = (2 * l) + (r * math.pi) - x elif x > l: arccos_val = (r - y) / math.sqrt((x ** 2) + ((y - r) ** 2)) x_trans = l + (r * math.acos(arccos_val)) # y变换方程 if x < 0: y_trans = math.sqrt((x ** 2) + ((y - r) ** 2)) - r elif 0 <= x <= l: y_trans = math.sqrt(((y - r) ** 2)) - r elif x > l: y_trans = math.sqrt(((x - l) ** 2) + ((y - r) ** 2)) - r return x_trans, y_trans
相关图示说明
- 数学方程图示:展示坐标变换的理论数学公式
- 原始坐标图示:展示待变换的原始坐标点分布
- 预期变换结果图示:展示坐标变换后的理想输出效果
- 实际输出结果图示:展示当前函数运行得到的实际输出效果
原代码问题排查
1. x变换方程错误
- x < 0 区域:分母计算错误,应计算点
(x,y)到圆心(0, r)的距离,原代码误用(x - l),导致距离计算偏差。 - x > l 区域:分母计算错误,应计算点
(x,y)到圆心(l, r)的距离,原代码误用x**2,导致距离计算偏差。
2. y变换方程错误
- 0 <= x <= l 区域:原代码计算为
|y - r| - r,结果存在偏移,正确计算应为y - r(直接保留y相对于圆心的偏移量)。
修正后的普通实现
import math def transformation_coord_fixed(x, y, l=4, r=3): x_trans = None y_trans = None # 修正后的x变换计算 if x < 0: dist = math.sqrt(x**2 + (y - r)**2) arccos_val = (r - y) / dist x_trans = 2 * l + r * math.pi + r * math.acos(arccos_val) elif 0 <= x <= l: x_trans = x if y < r else 2 * l + r * math.pi - x elif x > l: dist = math.sqrt((x - l)**2 + (y - r)**2) arccos_val = (r - y) / dist x_trans = l + r * math.acos(arccos_val) # 修正后的y变换计算 if x < 0: y_trans = math.sqrt(x**2 + (y - r)**2) - r elif 0 <= x <= l: y_trans = y - r elif x > l: y_trans = math.sqrt((x - l)**2 + (y - r)**2) - r return x_trans, y_trans
Numpy向量化实现
利用Numpy布尔索引批量处理坐标点,无需循环,效率更高:
import numpy as np def transformation_coord_numpy(x, y, l=4, r=3): # 初始化结果数组 x_trans = np.zeros_like(x, dtype=np.float64) y_trans = np.zeros_like(y, dtype=np.float64) # 定义各区域布尔掩码 mask_left = x < 0 mask_mid = (0 <= x) & (x <= l) mask_mid_lower = mask_mid & (y < r) mask_mid_upper = mask_mid & (y >= r) mask_right = x > l # 计算x变换结果 # 左区域 dist_left = np.sqrt(x[mask_left]**2 + (y[mask_left] - r)**2) arccos_left = (r - y[mask_left]) / dist_left x_trans[mask_left] = 2 * l + r * np.pi + r * np.arccos(arccos_left) # 中间下半区域 x_trans[mask_mid_lower] = x[mask_mid_lower] # 中间上半区域 x_trans[mask_mid_upper] = 2 * l + r * np.pi - x[mask_mid_upper] # 右区域 dist_right = np.sqrt((x[mask_right] - l)**2 + (y[mask_right] - r)**2) arccos_right = (r - y[mask_right]) / dist_right x_trans[mask_right] = l + r * np.arccos(arccos_right) # 计算y变换结果 # 左区域 y_trans[mask_left] = np.sqrt(x[mask_left]**2 + (y[mask_left] - r)**2) - r # 中间区域 y_trans[mask_mid] = y[mask_mid] - r # 右区域 y_trans[mask_right] = np.sqrt((x[mask_right] - l)**2 + (y[mask_right] - r)**2) - r return x_trans, y_trans
使用示例
# 单个点测试 x, y = -1, 3 x_t, y_t = transformation_coord_numpy(x, y) print(f"原始坐标({x},{y}) → 变换后坐标({x_t:.2f},{y_t:.2f})") # 批量点测试 x_arr = np.array([-2, 2, 5]) y_arr = np.array([0, 4, 3]) x_t_arr, y_t_arr = transformation_coord_numpy(x_arr, y_arr) print(f"原始坐标数组: {list(zip(x_arr, y_arr))}") print(f"变换后坐标数组: {list(zip(x_t_arr.round(2), y_t_arr.round(2)))}")
内容的提问来源于stack exchange,提问作者Rudina
相关产品推荐
相关产品推荐

