Tutorial 14
Click the badges above to run this tutorial interactively in your browser without installing anything!
- Binder: Free cloud-based Jupyter environment
- Colab: Google's free Jupyter notebook environment
Topics Covered
This tutorial covers the following topics using Python and SymPy:
- Stokes' theorem:
- Choosing the easier side of the identity
- Orientation: how the normal direction fixes the direction of travel around the boundary
- Verifying both sides of the theorem
- Surface integrals via a parametrisation
Introduction
Stokes' theorem lets you replace a hard surface integral with an easy line integral along the boundary — or the other way round. The two sides are only equal when the orientations match: with the right-hand rule, the normal determines the positive direction of travel around .
import sympy as sy
from sympy.abc import x, y, z, t, u, v, r, theta
from sympy import (sqrt, sin, cos, tan, pi, ln, exp, integrate, diff, simplify,
Rational, N, Matrix, Symbol)
sy.init_printing(use_latex=True)
def curl(F):
"""Curl of a 3D field given as a list/Matrix of components."""
return Matrix([diff(F[2], y) - diff(F[1], z),
diff(F[0], z) - diff(F[2], x),
diff(F[1], x) - diff(F[0], y)])
def line_integral(F, rx, ry, rz, t, t0, t1):
"""Integral of F . dr along (x,y,z) = (rx, ry, rz) for t in [t0, t1]."""
Fx = F[0].subs({x: rx, y: ry, z: rz})
Fy = F[1].subs({x: rx, y: ry, z: rz})
Fz = F[2].subs({x: rx, y: ry, z: rz})
return integrate(Fx*diff(rx, t) + Fy*diff(ry, t) + Fz*diff(rz, t), (t, t0, t1))
Question 1
, is the part of below , oriented with the outward normal. Compute .
The boundary is the circle in the plane . The natural parametrisation actually traverses , because with the outward normal the boundary must be walked clockwise.
F = Matrix([-y, x, z])
path = [3*cos(t), 3*sin(t), 4]
minus_C = line_integral(F, *path, t, 0, 2*pi)
display(minus_C) # 18*pi (this is the integral over -C)
display(-minus_C) # -18*pi (over C)
Question 2
, is the part of above , oriented upwards.
The boundary is the circle in the plane .
F = Matrix([z**2, -3*x*y, x**3*y**3])
I = line_integral(F, 2*cos(t), 2*sin(t), 1, t, 0, 2*pi)
display(simplify(I)) # 0
Question 3
and is the triangle with vertices , and , counterclockwise.
F = Matrix([z**2, y**2, x])
display(simplify(curl(F))) # <0, 2*z - 1, 0>
# the plane is x + y + z = 1, so z = 1 - x - y and the normal is <1, 1, 1>
integrand = simplify((curl(F).subs({z: 1 - x - y})).dot(Matrix([1, 1, 1])))
display(integrand) # 1 - 2*x - 2*y
I = integrate(integrand, (y, 0, 1 - x), (x, 0, 1))
display(I) # -1/6
Question 4
Verify Stokes' theorem for on the ellipse .
F = Matrix([x**2, 2*x, z**2])
path = [cos(t), 2*sin(t), 0] # counterclockwise ellipse, normal upwards
lhs = line_integral(F, *path, t, 0, 2*pi)
display(simplify(lhs)) # 4*pi
display(simplify(curl(F))) # <0, 0, 2>
rhs = 2 * (pi * 1 * 2) # 2 x area of the ellipse (pi*a*b)
display(rhs) # 4*pi
display(simplify(lhs - rhs)) # 0 -> verified
Both sides equal , so Stokes' theorem is verified.
Question 5
Verify Stokes' theorem for on the paraboloid with boundary .
F = Matrix([y**2, -x, 5*z])
display(simplify(curl(F))) # <0, 0, -1 - 2*y>
# surface side: normal < -2x, -2y, 1 >, integrand (-1 - 2y), over the unit disc
rhs = integrate((-1 - 2*r*sin(theta))*r, (r, 0, 1), (theta, 0, 2*pi))
display(simplify(rhs)) # -pi
# line side: x = cos t, y = sin t, z = 1
lhs = line_integral(F, cos(t), sin(t), 1, t, 0, 2*pi)
display(simplify(lhs)) # -pi
display(simplify(lhs - rhs)) # 0 -> verified
Both sides equal .
Question 6
, is the part of the ellipsoid below the -plane, and is the lower normal.
The boundary is the circle in the plane . A lower normal induces the clockwise orientation on the boundary.
F = Matrix([x*z**2, x**3, sy.cos(x*z)])
ccw = line_integral(F, cos(t), sin(t), 0, t, 0, 2*pi) # counterclockwise
display(ccw) # 3*pi/4
display(-ccw) # -3*pi/4 (clockwise)
The counterclockwise integral is , but the lower normal induces the clockwise orientation, so the answer is . The downloadable solution PDF still reports , having missed the orientation flip.
Question 7
, and is the intersection of the cylinder with the plane , counterclockwise when viewed from above.
F = Matrix([4*exp(x**2) - y, 16*sin(y**2) + 3*x, 4*y - 2*x - exp(z)])
cF = curl(F)
display(simplify(cF)) # <4, 2, 4>
# the plane z = 2x + 4y gives N dS = < -2, -4, 1 > dA
N = Matrix([-2, -4, 1])
display(simplify(cF.dot(N))) # -12
I = -12 * (pi * 4**2) # area of the disc of radius 4
display(I) # -192*pi
Differentiating the field literally gives , so and the answer is . The downloadable solution PDF instead reports the curl as , giving and .
Question 8
along , the intersection of the cylinder with the plane .
Parametrise the enclosed surface by with , .
rv = Matrix([u*cos(v), u*sin(v), 5 - u*cos(v)])
cross = rv.diff(u).cross(rv.diff(v))
display(simplify(cross)) # <u, 0, u>
F = Matrix([x*y, 2*z, 3*y])
display(simplify(curl(F))) # <1, 0, -x>
integrand = simplify(curl(F).subs({x: u*cos(v), y: u*sin(v), z: 5 - u*cos(v)}).dot(cross))
display(simplify(integrand)) # u - u**2*cos(v)
I = integrate(integrand, (v, 0, 2*pi), (u, 0, 3))
display(I) # 9*pi
Differentiating the field literally gives . The downloadable solution PDF writes , dropping the minus sign. The term integrates to zero over a full period, so the answer is unaffected by that sign error.
Question 9
where and is the part of inside and above the -plane.
The boundary is the circle of radius at height .
F = Matrix([y*z, x*z, x*y])
display(simplify(curl(F))) # <0, 0, 0> -> conservative field
I = line_integral(F, cos(t), sin(t), sqrt(3), t, 0, 2*pi)
display(simplify(I)) # 0
Extra Learning Resources
Key Concepts to Master
- Stokes' theorem: the flux of the curl through equals the circulation around
- The surface is your choice: any surface with the same boundary gives the same flux
- Orientation and the right-hand rule: with the normal up, the boundary is traversed counterclockwise
- Lower normal, clockwise boundary: reversing the normal reverses the direction of travel and flips the sign
- A zero curl means a conservative field, so the circulation around any closed loop is zero
SymPy Resources
- SymPy
cross— for - SymPy
subs— substituting the surface or the parametrisation - SymPy
integrate— the resulting single or double integral
Common Pitfalls
- Sign of the curl: differentiate each component literally; a dropped minus sign changes the answer (Q7)
- Orientation: always check whether the given normal induces a clockwise or counterclockwise boundary
- A surface integral over a disc is often just a constant times the area — recognise it before integrating
- If the answer is without any integration