Sympy中Curve平移结果不符预期的问题排查与解决
问题分析与解决方案
为什么at == b返回False?
有两个核心原因:
- 平移方向错误:你定义的
g(x) = -(x+5)² +8是f(x)向左平移5个单位、向上平移8个单位的结果;但Sympy的Curve.translate(dx, dy)是将曲线上每个点(x,y)变为(x+dx, y+dy)——dx为正值代表向右平移,因此你应该传入dx=-5而非5。 - Curve对象的相等性判断逻辑:Sympy对Curve的相等性判断是严格比较参数化表达式,而非判断两条曲线是否为同一个点集。即使平移方向正确,默认参数化的差异也会导致直接比较返回False。
正确的平移验证方法
方法1:修正平移方向+统一参数化后比较
先修正平移方向,再重新参数化平移后的曲线,让它的参数表达式与目标曲线一致:
from sympy import expand, Symbol, Curve, oo x = Symbol('x') f = -x**2 g = -(x+5)**2 + 8 a = Curve((x, f), (x, -oo, oo)) # 向左平移5(dx=-5),向上平移8(dy=8) at = a.translate(-5, 8) b = Curve((x, g), (x, -oo, oo)) # 重新参数化at:将at的横坐标替换为新符号t,匹配b的参数形式 t = Symbol('t') # at的横坐标是x-5 = t → 原参数x = t+5,代入at的纵坐标 at_reparam = Curve((t, at.functions[1].subs(x, t + 5)), (t, -oo, oo)) # 展开后比较纵坐标表达式 print(expand(at_reparam.functions[1]) == expand(b.functions[1])) # 输出True # 参数化一致后,Curve对象直接比较也会返回True print(at_reparam == b) # 输出True
方法2:验证点集等价性
不依赖参数化形式,直接判断两条曲线的点集是否完全重合:
from sympy import ForAll, exists, Eq t = Symbol('t') # 逻辑:对于任意横坐标x,b上的点(x, g(x))必然存在参数t,使得它是at上的点(t-5, -t²+8) condition = ForAll(x, exists(t, Eq((x, g(x)), (t-5, -t**2 + 8)))) print(condition) # 输出True
方法3:比较隐式方程
将两条曲线转换为隐式方程,通过比较隐式方程判断是否为同一条曲线:
from sympy import solve, Symbol y = Symbol('y') # 推导at的隐式方程 at_implicit = solve(Eq(at.functions[1], y), y)[0] - y # 推导b的隐式方程 b_implicit = solve(Eq(b.functions[1], y), y)[0] - y # 展开后比较隐式方程 print(expand(at_implicit) == expand(b_implicit)) # 输出True
内容的提问来源于stack exchange,提问作者marcelo.guedes
相关产品推荐
相关产品推荐

