Solución:
Hacer esto puede hacer que se pierda algo importante, pero, para silenciar el mensaje de advertencia, puede usar warnings.filterwarnings
:
import warnings
warnings.filterwarnings('ignore', 'The iteration is not making good progress')
import math
from scipy.optimize import fsolve
import numpy as np
def p(s, l, k, q):
p = q * np.maximum(s - k, 0.0)
return (p + math.copysign(l, -q)) * math.fabs(q) * 100.0
x0 = fsolve(p, np.arange(33.86, 50.86, 1.0),
args=(1.42, 41.0, -1.0), xtol=1e-06, maxfev=500)
print(x0)
De hecho, p(x0, 1.42, 41.0, -1)
no está cerca de cero, entonces fsolve
le está advirtiendo correctamente que no pudo encontrar una solución.
PD. Cuando tu dices
fsolve(p, np.arange(33.86, 50.86, 1.0),...)
estás diciendo fsolve
que tu conjetura inicial para s
es la matriz numpy np.arange(33.86, 50.86, 1.0)
. Toda la matriz se pasa a p
En seguida.
Darse cuenta de np.arange(33.86, 50.86, 1.0)
tiene una longitud de 17 y también la tiene x0
. Eso es porque fsolve
piensa que está buscando una matriz de longitud 17 que resuelva p
.
Creo que tal vez quisiste decir s
ser un flotador? En ese caso, solo puede pasar un valor flotante para su suposición inicial:
fsolve(p, 41.0, args = (1.42, 41.0, -1.0), xtol=1e-06, maxfev=500)
Por ejemplo,
import math
import scipy.optimize as optimize
import numpy as np
def p(s, l, k, q):
p = q * np.maximum(s - k, 0.0)
return (p + math.copysign(l, -q)) * math.fabs(q) * 100.0
args = (1.42, 41.0, -1.0)
result = optimize.fsolve(p, 41.0, args=args, xtol=1e-06, maxfev=500)
print(result)
rendimientos
[ 42.42]
fsolve
hace un trabajo decente al poner a cero en la raíz si la estimación inicial es> = 41.0 (el valor de k
) pero falla cuando la estimación inicial es <41.0.
Supongo que esto se debe a np.maximum
no cambia para muchas conjeturas para s
. Entonces fsolve
no sabe si aumentar o disminuir s
y tiende a adivinar mal y moverse s
cada vez más lejos de la raíz.