3

I have defined a function integrate_boole as follows:

def integrate_boole(f,l,r,N):
N = 4 * int(N // 4)
h=((r-l)/N)
xN = np.linspace(l,r,N+1)
fN = f(xN)
return ((2*h)/45)*(7*fN[0]+32*(np.sum(fN[1:-1:2]))+12*. (np.sum(fN[2:-2:4]))+14*(np.sum(fN[4:-4]))+7*fN[-1])

I'm now trying to integrate between 0 and pi for f(x), where f(x) is defined as:

def f(x):
return x*np.sin(x)/(1+np.cos(x)**2)

When I substitute f(x) into the function:

integrate_boole(f(x),0,np.pi,8)

I get the following error message:

-----------------------------------------------------------------------  ----
AttributeError                            Traceback (most recent call    last)
<ipython-input-23-91f1a95793b5> in <module>()
----> 1 integrate_boole(f(x),0,np.pi,8)

 <ipython-input-20-165d275ae26c> in f(x)
  1 def f(x):
----> 2     return x*np.sin(x)/(1+np.cos(x)**2)
  3 myx = np.linspace(0,np.pi,1000)
  4 plt.plot(myx,f(myx),label=r"$f(x)=\frac{x\sin{x}}{1+\cos^2{x}}$")
  5 plt.ylabel("$f(x)$")

AttributeError: 'Symbol' object has no attribute 'sin'

I imported the following libraries initially at the beginning of the same notebook:

import numpy as np
import matplotlib.pyplot as plt
import sympy as sym
from ipywidgets.widgets import interact
sym.init_printing(use_latex="mathjax")
x, y, z, t = sym.symbols('x y z t')

I've checked other articles about roughly the same subject, however I don't believe my numpy and sympy libraries are clashing as they seem to have done for other people. But they might be, and I don't know why. Any help would be much appreciated.

yerman
  • 267
  • 2
  • 4
  • 12
  • You are mixing numpy and sympy. Numpy routines usually do not know what to do with symbols, but you can replace some of the function calls with their sympy equivalents... e.g. `sym.sin` – MB-F Nov 29 '18 at 10:51
  • When `np.sin` is given an object dtype array (or a list that would make such an array) tries to call `e.sin()` on each element of the array. Hence the attribute error if the object doesn't have that method. Evidently here you've provided an array or list of Symbols. – hpaulj Nov 29 '18 at 17:33

1 Answers1

1

The first argument of integrate_boole should be a function.

  • f is a function
  • f(x) is the number returned by the function f for input x.

You need to call

integrate_boole(f,0,np.pi,8)

and not

integrate_boole(f(x),0,np.pi,8)

Here's the complete code, with correct indentation:

import numpy as np
import matplotlib.pyplot as plt
import sympy as sym

x, y, z, t = sym.symbols('x y z t')

def integrate_boole(f,l,r,N):
    N = 4 * int(N // 4)
    h=((r-l)/N)
    xN = np.linspace(l,r,N+1)
    fN = f(xN)
    return ((2*h)/45)*(7*fN[0]+32*(np.sum(fN[1:-1:2]))+12*(np.sum(fN[2:-2:4]))+14*(np.sum(fN[4:-4]))+7*fN[-1])

def f(x):
    return x*np.sin(x)/(1+np.cos(x)**2)

integrate_boole(f,0,np.pi,8)
# 2.470207745145361
Eric Duminil
  • 52,989
  • 9
  • 71
  • 124