2015-12-01 28 views
0

У меня есть уравнение:Python SciPy fsolve работает неправильно

import numpy as np 
from scipy import optimize 

def wealth_evolution(price, wealth=10, rate=0.01, q=1, realEstate=0.1, prev_price=56): 
    sum_wantedEstate = 100 
    for delta in range(1,4): 
     z = rate - ((price-prev_price)/(price + q/rate)) 
     k = delta * np.divide(1.0, float(np.maximum(0.0, z))) 
     wantedEstate = (wealth/(price + q/rate)) * np.minimum(k, 1) - realEstate 
     sum_wantedEstate += wantedEstate 
    return sum_wantedEstate 

Так что найти решение этого уравнения:

sol = optimize.fsolve(wealth_evolution, 200) 

Но если я заменял sol в уравнение я бы не получить 0 (welth_evolution(sol)). Почему так происходит? fsolve находит корни f(x)=0.

UPD: full_output дает:

(array([ 2585200.]), {'qtf': array([-99.70002298]), 'nfev': 14, 'fjac': array([[-1.]]), 'r': array([ 3.45456519e-11]), 'fvec': array([ 99.7000116])}, 5, 'The iteration is not making good progress, as measured by the \n improvement from the last ten iterations.') 
+1

Возможно, вы захотите показать [mcve] – cel

+1

Было бы полезно, если бы вы разместили вывод отладки, созданный 'full_info = True'. –

+0

@cel Фактически, это довольно близко, как есть. Запустите код и проверьте результат с помощью 'wealth_evolution (sol)'. –

ответ

3

Пытались ли вы черчение вашей функции?

import numpy as np 
from scipy import optimize 
from matplotlib import pyplot as plt 
small = 1e-30 
def wealth_evolution(price, wealth=10, rate=0.01, q=1, realEstate=0.1, prev_price=56): 
    sum_wantedEstate = 100 
    for delta in range(1,4): 
     z = rate - ((price-prev_price)/(price + q/rate)) 
     k = delta * np.divide(1.0, float(np.maximum(small, z))) 
     wantedEstate = (wealth/(price + q/rate)) * np.minimum(k, 1) - realEstate 
     sum_wantedEstate += wantedEstate 
    return sum_wantedEstate 




price_range = np.linspace(0,10000,10000) 
we = [wealth_evolution(p) for p in price_range] 

plt.plot(price_range,we) 
plt.xlabel('price') 
plt.ylabel('wealth_evolution(price)') 
plt.show() 

enter image description here

По крайней мере, для параметров вы указываете, что не имеет корня, что и fsolve пытается найти. Если вы хотите свести к минимуму функцию, вы можете попробовать fmin. Для этой функции это не поможет, потому что, похоже, просто асимптотически распад до 99,7 или около того. Таким образом, сведение к минимуму привело бы к бесконечности цена.

Так как вы должны жить с этим или придумать другую функцию для оптимизации или ограничить диапазон поиска (в этом случае вам не придется искать, потому что это только будет максимальное значение ...).

+0

Меня всегда удивляет, что люди используют хороший интерактивный инструмент, такой как Python, и затем ожидают, что он волшебным образом найдет то, что они «знают», не проверив (по графику), что он на самом деле есть. Вы всегда должны строить свои функции! Это должно дать вам очень хорошую информацию о том, какой решатель (или минимизатор) использовать, и хорошие идеи о том, где начать поиск. По сравнению со днями программ Fortran, запущенных на картах (да, я сделал это), это так легко сделать сейчас. –

Смежные вопросы