TypeError: only size-1 arrays can be converted to Python scalars - Printable Version +- Python Forum (https://python-forum.io) +-- Forum: Python Coding (https://python-forum.io/forum-7.html) +--- Forum: Homework (https://python-forum.io/forum-9.html) +--- Thread: TypeError: only size-1 arrays can be converted to Python scalars (/thread-30646.html) |
TypeError: only size-1 arrays can be converted to Python scalars - RainbowTrish1 - Oct-29-2020 Hi everyone, Hope ye are all well. I am extremely new to Python and have an assignment due tomorrow which I really struggled with, but happy at how much I have accomplished. However, I am trying to plot the 3 functions for my newton raphson method. My first function was fine but the 2nd and 3rd one won't because of this error: TypeError: only size-1 arrays can be converted to Python scalars And I have been trying to fix it but not getting very war so any help would be greatly appreciated. Here is the code I have written: import numpy as np import scipy as sc ##complex numbers import matplotlib.pyplot as plt import math as math def newton_r(f, dfdx, x0, TOL, NO): n = 1 print("n \t x_n \t x \t f_x \t dfdx_x \t ") print("%2.0f \t %2.10f " % (n, x0)) x = f(x0) #evaluate function at initial guess and get output X while (np.abs(x) > TOL): n = n + 1 x = x0 - f(x0) / dfdx(x0) x0 = x ##bringing initial value up to a new point FX = f(x0) if FX == 0 or x < TOL: print("The root is %.10f at %d iterations." %(x0, n)) return x0 if (np.imag(x) != 0): print("Error: Trying to compute the square root of a negative number") break elif (n >= NO): print("Maximum number of steps reached") break print("%2.0f %.10f %.10f %.10f %.10f" % (n, x0, x, f(x0), dfdx(x0))) f1 = lambda x: x**3 + 4*x**2 - 10 dfdx1 = lambda x: 3*x**2 + 8*x f2 = lambda x: ((1/x) + (math.log(x + 1)) - 5) dfdx2 = lambda x: (1/(x + 1) - 1/x**2) f3 = lambda x: ((math.log(x)) + (math.exp(x))) dfdx3 = lambda x: ((1/x) + (math.exp(x))) ##Question 1: Plot each function and all approximations of the root ## setup for f1 x1 = np.linspace(0.0, 3, 100) ##this is giving me an array(list) called x1 that's filled with 100 values y1 = x1**3 + 4*x1**2 - 10/3*x1**2 + 8*x1 ##equally spaced between the intervals of 0.5 - 2 x2 = np.linspace(0.1, 3, 100) y2 = ((1/x2) + (math.log((x2 + 1)) - 5) / (1/(x2 + 1)) - 1/(x2**2)) ##x3 = np.linspace(0.2, 2, 100) #y3 = ((math.log(x3)) + (math.exp(x3))) / ((1/x3) + (math.exp(x3))) plt.figure(figsize =(10,5)) plt.subplot(3,2,1) ##setting dimensions of subplot plt.plot(x1, y1, color='b') plt.ylim(-10,60) ##setting y-axis scale plt.axhline(0, color = 'k', lineWidth = 1.0) #this command will create an origin at y = 0 plt.axvline(0, color = 'k', lineWidth = 1.0) #this command will create a vertical line at x = 0 plt.ylabel('y1', color="r") ##y-axis label, with the text being the colour red plt.xlabel('x',horizontalalignment='right', x=1.0, color="r") plt.grid(True) ##setting grid lines plt.tight_layout() ##better spacing between graphs, as they were on top of each other!!!!FOR Y2 AND YS ABOVE IS WHERE THE ERROR IN MY CODE LAYS, WITH THE ABOVE MENTIONED ERROR. IF SOMEONE HAS ANY ADVICE ON HOW TO ADJUST AND RESOLVE THIS I CAN'T TELL YOU HOW GRATEFUL I WOULD BE. Kind Regards, Kate RE: TypeError: only size-1 arrays can be converted to Python scalars - DeaD_EyE - Oct-29-2020 Use np.log instead of math.log. I also removed not used imports. Also the line "import math as math" is useless. First you import math and then math is renamed to math. Then use f-strings or str.format instead of the % formatting.Don't assign lambda (anonymous function) to a name. Use def for function definition instead. Lambdas are used for example in place as an argument of a function call for example: some_data = [("y", 10), ("a", 20)] some_data_sorted_by_second_key = sorted(some_data, key=lambda x: x[1])Here your modified code. I haven't changed the rest. This is your task. import math import matplotlib.pyplot as plt import numpy as np def newton_r(f, dfdx, x0, TOL, NO): """ Provide a description """ n = 1 print("n \t x_n \t x \t f_x \t dfdx_x \t ") print("%2.0f \t %2.10f " % (n, x0)) x = f(x0) # evaluate function at initial guess and get output X while np.abs(x) > TOL: n = n + 1 x = x0 - f(x0) / dfdx(x0) x0 = x ##bringing initial value up to a new point FX = f(x0) if FX == 0 or x < TOL: print("The root is %.10f at %d iterations." % (x0, n)) return x0 if np.imag(x) != 0: print("Error: Trying to compute the square root of a negative number") break elif n >= NO: print("Maximum number of steps reached") break print( "%2.0f %.10f %.10f %.10f %.10f" % (n, x0, x, f(x0), dfdx(x0)) ) # old style formatting was used 15 years ago # now we've the format method of str # and f-strings # named functions should be defined with def # using lambdas is not the right way if you assing it to a name f1 = lambda x: x ** 3 + 4 * x ** 2 - 10 dfdx1 = lambda x: 3 * x ** 2 + 8 * x f2 = lambda x: ((1 / x) + (math.log(x + 1)) - 5) dfdx2 = lambda x: (1 / (x + 1) - 1 / x ** 2) f3 = lambda x: ((math.log(x)) + (math.exp(x))) dfdx3 = lambda x: ((1 / x) + (math.exp(x))) ##Question 1: Plot each function and all approximations of the root ## setup for f1 x1 = np.linspace( 0.0, 3, 100 ) ##this is giving me an array(list) called x1 that's filled with 100 values y1 = ( x1 ** 3 + 4 * x1 ** 2 - 10 / 3 * x1 ** 2 + 8 * x1 ) ##equally spaced between the intervals of 0.5 - 2 x2 = np.linspace(0.1, 3, 100) y2 = (1 / x2) + (np.log((x2 + 1)) - 5) / (1 / (x2 + 1)) - 1 / (x2 ** 2) ##x3 = np.linspace(0.2, 2, 100) # y3 = ((math.log(x3)) + (math.exp(x3))) / ((1/x3) + (math.exp(x3))) plt.figure(figsize=(10, 5)) plt.subplot(3, 2, 1) ##setting dimensions of subplot plt.plot(x1, y1, color="b") plt.ylim(-10, 60) ##setting y-axis scale plt.axhline(0, color="k", lineWidth=1.0) # this command will create an origin at y = 0 plt.axvline( 0, color="k", lineWidth=1.0 ) # this command will create a vertical line at x = 0 plt.ylabel("y1", color="r") ##y-axis label, with the text being the colour red plt.xlabel("x", horizontalalignment="right", x=1.0, color="r") plt.grid(True) ##setting grid lines plt.tight_layout() ##better spacing between graphs, as they were on top of each other plt.show()[attachment=1034] |