简体   繁体   中英

Scipy Optimize ValueError: Too many variables to unpack

Trying to use the root method in scipy.optimize but keep getting a ValueError although to me it seems as I have entered the correct number of variables.

import numpy as np
from scipy import optimize
earthpos=np.array([  1.50000000e+11,   0.00000000e+00,   0.00000000e+00])

def equations(p,qf):
    q1, q2, q3, q4 = p
    r1=np.sqrt((qf[0]-mu2)**2+qf[1]**2+qf[2]**2)
    return q1**2-q2**2-q3**2+q4**2-qf[0]+mu2, 2*q1*q2-2*q3*q4-qf[1], 2*q1*q3+2*q2*q4-qf[2], q1**2+q2**2+q3**2+q4**2-r1

q1, q2, q3, q4 = optimize.root(equations, (1,1,1,1),earthpos)

Gives:

 ValueError: too many values to unpack (expected 4)

Why you get the error

You get the error because optimize.root() returns a scipy optimization results. Type type(optimize.root(equations, (1,1,1,1),earthpos)) and see the output.

How to solve and unpack the solution of the optimization

Replace the last line

q1, q2, q3, q4 = optimize.root(equations, (1,1,1,1),earthpos)

with

q1, q2, q3, q4 = optimize.root(equations, (1,1,1,1),earthpos).x

By using .x at the end, you unpack the solution ie x from the OptimizeResult object.


Putting all together, you just need this:

import numpy as np
from scipy import optimize
earthpos=np.array([  1.50000000e+11,   0.00000000e+00,   0.00000000e+00])

def equations(p,qf):
    q1, q2, q3, q4 = p
    r1=np.sqrt((qf[0]-mu2)**2+qf[1]**2+qf[2]**2)
    return q1**2-q2**2-q3**2+q4**2-qf[0]+mu2, 2*q1*q2-2*q3*q4-qf[1], 2*q1*q3+2*q2*q4-qf[2], q1**2+q2**2+q3**2+q4**2-r1

q1, q2, q3, q4 = optimize.root(equations, (1,1,1,1),earthpos).x

It seems that optimize.root returns an OptimizeResult object:

Returns:
solOptimizeResult:
The solution represented as a OptimizeResult object. Important attributes are: x the solution array, success a Boolean flag indicating if the algorithm exited successfully and message which describes the cause of the termination. See OptimizeResult for a description of other attributes.

See here: https://docs.scipy.org/doc/scipy/reference/generated/scipy.optimize.OptimizeResult.html#scipy.optimize.OptimizeResult

The object is made up of more than 4 fields, the field that you are looking for is the first one, so maybe optimize.root(equations, (1,1,1,1),earthpos)[0] will work? I'm sorry if this doesn't work, it's been a long time since I have programmed in Python.

Your example is not runnable since you do not specify mu2 .

Read the examples in the documentation for root . Also read the attributes of the OptimizeResult object that is returned by root As pointed out by Abs, optimize.root returns an object, but you must use the x attribute of said object to access the solution.

You want to do something like (I used mu2=1 ):

import numpy as np
from scipy import optimize
mu2 = 1
earthpos=np.array([  1.50000000e+11,   0.00000000e+00,   0.00000000e+00])
def equations(p,qf):
    q1, q2, q3, q4 = p
    r1=np.sqrt((qf[0]-mu2)**2+qf[1]**2+qf[2]**2)
    return q1**2-q2**2-q3**2+q4**2-qf[0]+mu2, 2*q1*q2-2*q3*q4-qf[1], 2*q1*q3+2*q2*q4-qf[2], q1**2+q2**2+q3**2+q4**2-r1
sol = optimize.root(equations, (1,1,1,1),earthpos)
q1, q2, q3, q4 = sol.x
print(q1)

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM