[英]Combining Sympy with scipy.optimize.least_squares
我正在嘗試計算 function E 達到其最小值的變量D和theta的值。
E = sqrt(x1-Dcos(theta)^2 + (y1-Dsin(theta)^2)) + sqrt(x2-2Dcos(theta)^2 + (y2-2Dsin(theta)^2)) + sqrt(x3-3Dcos(theta)^2 + (y3-3Dsin(theta)^2))
。
這里,(x1,y1), (x2,y2), (x3,y3) 是已知的。 現在我計算 E wrt 對 D 和 theta 的偏導數並將它們設置為零。 現在我有 2 個方程和 2 個未知數,所以理論上這個系統應該是完全可解的。 這里唯一的問題是這是高度非線性的。 所以分析解決方案是不可能的。 我在這里使用 Sympy 來計算偏導數並從 scipy.optimize 生成要在最小二乘法中使用的方程。 我確實得到了 D 和 theta 的解決方案,但它沒有任何物理意義。 此外,least_squares 的成本值約為 17,所以我的解決方案不是很可靠,對吧? 有人可以幫我嗎? 這是代碼:
import sympy as sym
D, theta = sym.symbols("D, theta")
x1,x2,x3 = 9.0,22.0,24.0
y1,y2,y3 = 14.0,14.0,14.0
E = ((x1-D*sym.cos(theta))**2 + (y1-D*sym.sin(theta))**2)**0.5 + ((x2-2*D*sym.cos(theta))**2 + (y2-2*D*sym.sin(theta))**2)**0.5 + ((x3-3*D*sym.cos(theta))**2 + (y3-3*D*sym.sin(theta))**2)**0.5
gradient = sym.derive_by_array(E, (D, theta))
from scipy.optimize import least_squares as ls
grad = sym.lambdify((D, theta), gradient)
A = ls(lambda v: grad(v[0],v[1]), (8,0), bounds=([0, -22.5*np.pi/180], [12, 22.5*np.pi/180])) #theta should be between -22.5 degree and 22.5 degree and D should be between 0 and 12 but ideally not 0.
D2, theta2 = A.x # 0.04561884938833529 -0.3926990816987241
我還應該提到,計算D和theta是涉及擬合通過 (x1,y1)、(x2,y2)、(x3,y3) 和 (13,2) 的線的問題的一部分。 D 是擬合線上 (13,2) 和最接近 (x1,y1) 的第一個點之間的距離,2D 是類似地是 (13,2) 和最接近 (x2,y2) 的第二個點之間的距離,以及很快。 必須對大小為 (21,69) 的經緯網格上的所有網格點進行此分析。 也歡迎所有解決此問題的替代建議。 提前致謝!
您正在尋找使用等距序列(如11,18,25
9, 22, 24
。 這沒有很好的擬合,因此較大的殘值是合理的。
Doing the least square sum manually gives
(a-d-9)^2 + (a-22)^2 + (a+d-24)^2 = 3*a^2 +2*d^2 - 110*a - 30*d +const
so the optimum is at a = 55/3 = 18+1/3 and d = 15/2 = 7+1/2
再看一眼,您試圖最小化范數之和,即從平行於x
軸的線上的點到通過原點的線上等距的點的距離之和。 您可以在不進行任何最小二乘梯度優化的情況下做到這一點(無論如何這都是一個奇怪的想法,為什么不直接使用fsolve
找到梯度的零位置?)
x = np.array([ 9.0,22.0,24.0])
y = np.array([14.0,14.0,14.0])
K = 1+np.arange(len(x))
target = lambda X,Y: sum(np.hypot(x-K*X, y-K*Y))
from scipy.optimize import fmin, minimize
#U = fmin(lambda u: target(*u), [4,4])
U = minimize(lambda u: target(*u), [4,4])
print(U)
X,Y = U.x
print(X,Y, np.hypot(X,Y), np.arctan2(Y,X))
K = np.arange(1+len(x))
plt.plot(x,y,'o', ms=8); plt.plot(K*X,K*Y, '-s', ms=4); plt.grid(); plt.show()
結果
fmin:
-----
Optimization terminated successfully.
Current function value: 16.987937
Iterations: 49
Function evaluations: 92
minimize:
---------
fun: 16.987921401556633
hess_inv: array([[2.72893764e-08, 6.01803467e-08],
[6.01803467e-08, 1.53257534e-07]])
jac: array([ 1.29665709, -0.08849001])
message: 'Desired error not necessarily achieved due to precision loss.'
nfev: 740
nit: 29
njev: 182
status: 2
success: False
x: array([8. , 4.66666667])
X: 8.000000, Y: 4.666667,
D: 9.261629, theta: 0.5280744
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.