TypeError: only length-1 arrays can be converted to Python scalars

0
import matplotlib.pyplot as plt
import numpy as np
from py_expression_eval import *

def f(exp, var, x0):
    p = Parser()
    result = p.parse(exp).evaluate({var:x0})
    return result
a = 0
b = 4
error = 10
i = 0
while(error>1e-8 and i!=100):
    c = (a + b) / 2
    fa = f('x^3 -2 * x^2 - 1', 'x', a)
    fc = f('x^3 -2 * x^2 - 1', 'x', c)
    if(fc == 0):
        raiz = c
        break
    elif(fa * fc < 0):
        b = c
    else:
        a = c
    raiz = c
    i += 1
    error = abs(fc)
    print("Iteracion",i,". Raiz aproximada:",raiz)
print(raiz)
print(i)
print(f('x^3 -2 * x^2 - 1', 'x',raiz))

x = np.linspace(0, 4, 101)
print(x)
plt.plot(x, f('x^3 -2 * x^2 - 1','x',x))
plt.plot(a, f('x^3 -2 * x^2 - 1', 'x', a), 'or')
plt.grid()
plt.show()

It tells me the error of the title when trying to graph after implementing the expression evaluator, before I had no problem with the following code:

import matplotlib.pyplot as plt
import numpy as np
import py_expression_eval

def f(x):
    return x**3 -2 * x ** 2 - 1
a = 0
b = 4
error = 10
i = 0
while(error>1e-8 and i!=100):
    c = (a + b) / 2
    fa = f(a)
    fc = f(c)
    if(fc == 0):
        raiz = c
        break
    elif(fa * fc < 0):
        b = c
    else:
        a = c
    raiz = c
    i += 1
    error = abs(fc)
    print("Intervalo ("+str(a) + "," + str(b) +")" )
    print("Iteracion",i,". Raiz aproximada:",raiz)
print(raiz)
print(i)
print(f(2.2055694311857224))
x = np.linspace(0, 4, 101)
plt.plot(x, f(x))
plt.grid()
plt.show()

If someone can help me to work with the expression eval I thank you in advance.

The complete error message is this:

  

Traceback (most recent call last):

     

File "C: \ Users \ Daniel \ Desktop \ bisection3.py", line 34, in

     

plt.plot(x, f('x^3 -2 * x^2 - 1','x',x))

     

File "C: \ Users \ Daniel \ Desktop \ bisection3.py", line 7, in f

     

result = p.parse(exp).evaluate({var:x0})

     

File "C: \ Users \ Daniel \ AppData \ Local \ Programs \ Python \ Python36-32 \ lib \ site-packages \ py_expression_eval__init __. py", line 122, in eval       nstack.append (f (n1, n2))

     

TypeError: only length-1 arrays can be converted to Python scalars

If I try to convert x to int before passing it to the function to be plotted, it gives me the same error of the title, it has something to do with the type of data but it is not: (

    
asked by Daniel V 02.03.2017 в 11:23
source

1 answer

0

It is a common error when you mix arrays of NumPy and certain mathematical operations native or defined in the standard Python library as math.sqrt() .

In your case the problem originates in the line:

plt.plot(x, f('x^3 -2 * x^2 - 1','x',x))

The problem is interestingly the enhancement operation, ^ which causes the problem because it expects scalars as input parameters but you are passing an array of Numpy :

x = np.linspace(0, 4, 101)

The solution in these cases is usually to replace the problematic function with its equivalent in the library Numpy and if it accepts as an input parameter arrays of NumPy . In this case the analog of ^ is numpy.power() , for this you can modify the operator that will use evaluate modifying ops2 :

parser.ops2['^'] = np.power

The code would look like this:

import matplotlib.pyplot as plt
import numpy as np
from py_expression_eval import *

def f(exp, var, x0):
    p = Parser()
    p.ops2['^'] = np.power
    result = p.parse(exp).evaluate({var:x0})
    return result

a = 0
b = 4
error = 10
i = 0
while(error>1e-8 and i!=100):
    c = (a + b) / 2
    fa = f('x^3 -2 * x^2 - 1', 'x', a)
    fc = f('x^3 -2 * x^2 - 1', 'x', c)
    if(fc == 0):
        raiz = c
        break
    elif(fa * fc < 0):
        b = c
    else:
        a = c
    raiz = c
    i += 1
    error = abs(fc)
    print("Iteracion",i,". Raiz aproximada:",raiz)
print(raiz)
print(i)
print(f('x^3 -2 * x^2 - 1', 'x',raiz))

x = np.linspace(0, 4, 101)
print(x)
plt.plot(x, f('x^3 -2 * x^2 - 1','x',x))
plt.plot(a, f('x^3 -2 * x^2 - 1', 'x', a), 'or')
plt.grid()
plt.show()

What it shows:

    
answered by 02.03.2017 / 22:19
source