You are on page 1of 56

See discussions, stats, and author profiles for this publication at: https://www.researchgate.

net/publication/351130364

Computational Quantum Mechanics Using Scilab

Book · April 2021

CITATIONS READS

0 918

4 authors:

Rithwik Ranganathan Antariksha Mitra


King's College London Birla Institute of Technology, Mesra
3 PUBLICATIONS 0 CITATIONS 1 PUBLICATION 0 CITATIONS

SEE PROFILE SEE PROFILE

Sourabh Barua Devotosh Ganguly


Indian Institute of Technology Kanpur University of Alberta
14 PUBLICATIONS 378 CITATIONS 3 PUBLICATIONS 0 CITATIONS

SEE PROFILE SEE PROFILE

All content following this page was uploaded by Rithwik Ranganathan on 28 April 2021.

The user has requested enhancement of the downloaded file.


BIT Mesra
Department of Physics

Computational Quantum Mechanics

Using Scilab

Author and Editor


Sourabh Barua
Contributing Authors
Devotosh Ganguly
Antariksha Mitra
Rithwik R

April 28, 2021


Contents

1 Initial Value Problem Devotosh Ganguly 2


1.1 Solving initial value problem . . . . . . . . . . . . . . . . . . . . . . . . . . 2
1.1.1 Example 1 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 2
1.1.2 Example 2 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 3
1.1.3 Example 3 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 4
1.1.4 Example 4 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 6
1.1.5 Example 5 . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 7

2 Shooting Method (to solve boundary value problems) Sourabh Barua 9


2.0.1 Programme . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 10
2.0.2 Output . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 12
2.0.3 Using inbuilt root solver function . . . . . . . . . . . . . . . . . . . 12

3 Shooting Method for Schrodinger Equation Sourabh Barua 15


3.0.1 Programme . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 16
3.0.2 Output . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 20
3.0.3 Diverging of solutions . . . . . . . . . . . . . . . . . . . . . . . . . . 20

4 The Harmonic Oscillator Problem Sourabh Barua 24


4.0.1 Programme . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 25
4.0.2 Output . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 27
4.0.3 Diverging of solutions . . . . . . . . . . . . . . . . . . . . . . . . . . 29

5 Radial Schrodinger equation: Hydrogen atom Sourabh Barua 32


5.0.1 Programme . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 33
5.0.2 Output . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 36

6 The Anharmonic Oscillator Problem Rithwik R 38

7 Some More Potentials Antariksha Mitra 44


7.1 Coulumb Screening . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 44
7.1.1 Programme . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 45
7.1.2 Output . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 46
7.2 Double Well . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 47
7.2.1 Programme . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 47
7.2.2 Output . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 50

i
About the Authors

Devotosh Ganguly Devotosh is a final semester B.Sc. Physics student


at Birla Institute of Technology. A motivated individual with good an-
alytical and learning skills, he always looks to learn and grow and make
himself able to contribute in the field of science by whichever way he can.
Computational physics has been a favorite thing for him and he loves
simulating and modelling stuffs. He has been an ex summer fellowship
holder in the Indian Academy of sciences and loves working on problems
that enhances understanding of various physical problems.

Rithwik R is a final year Bsc student at BIT Mesra. His area


of interest is in the field of Non-equilibrium statistical physics, in-
formation theory and open quantum systems. In addition he is
also interested in theoretical computer science and algorithm design-
ing.

Antariksha Mitra. Interested in Astrophysics and Programming to be


specific, but enriching self with knowledge on anything everything is a
matter of joy and pride. Well You see I want to find the Key to the Lock
and not the Lock to the key, the skills I have today is not to be used
as the key to find its Lock ,rather the skills I have today are to be used
as the source to prepare the Key to open the Locks of this Mysterious
World.

Sourabh Barua is a TEQIP sponsored Assistant Professor at Birla In-


stitute of Technology Mesra, Ranchi. His current interest is in learning
and using density functional theory using the open source code quantum-
espresso. He has taught this quantum mechanics lab course for the first
time and this manual is a record of sorts of the progress made during the
lab course held in spring 2021 in fully online mode.

1
Chapter 1

Initial Value Problem

Initial value problems are ordinary differential equations where the initial conditions are
given. For example in a second order differential equation the value of the dependent vari-
able and its first derivative at the initial value of the independent variable is given.

1.1 Solving initial value problem


The function ode in scilab can be used to solve first order and higher order ordinary
differential equations (ode). Following example problems are from the textbook [1] .

1.1.1 Example 1
//Integrate the initial value problem
//y'+4y=x^2 y(0)=1
//x=[0, 0.03]
clc
y0=1;
x=0:0.01:5
function dy =f(x,y)
dy= x^2-4*y;
endfunction
sol=ode(y0,x(1),x,f);
disp(sol);
disp(x);
plot(x,sol,'kx');
xlabel('x','fontsize',3)
ylabel('y','fontsize',3)
title("Plot for ODE","fontsize",3)
legend("y(x)")
xgrid()

2
1.1.2 Example 2
//y"=-0.1y'-x
//y(0)=0 y'(0)=1
clc
x=0:0.05:2
y0=[0;1]
function dy=f(x,y)
dy(1)=y(2)
dy(2)=-0.1*y(2)-x
endfunction
sol=ode(y0,x(1),x,f);
disp(sol);
y=sol(1,:);
disp(y)
disp(y(2))
y_exact=100*x-5*x^2+990*(exp(-0.1*x)-1);
plot(x,y,'rx');
plot(x,y_exact,'b');
xlabel('x','fontsize',3)
ylabel('y','fontsize',3)

3
title("Plot for ODE","fontsize",3)
legend("Computational value of y","Analytical solution of y")

1.1.3 Example 3
//Integrate the problems from x=0 to 20
//(a) y"+0.5(y^2-1)+y=0 y(0)=1, y'(0)=0
//(b) y"=y*cos2x y(0)=0,y'(0)=1
//(a)
clc
x=0:0.1:20
y0=[0;1]
function dy=f(x,y)
dy(1)=y(2)
dy(2)=-y(1)-0.5*(y(1)^2-1)
endfunction
sol=ode(y0,0,x,f);
subplot(2,1,1)
plot(x,sol(1,:),'rx')
plot(x,sol(2,:),'kx')
xlabel('x','fontsize',3)
ylabel("y(x) and dy(x)/dx","fontsize",3)

4
title("Plot for ODE (a)","fontsize",3)
legend("y(x)","dy(x)/dx")

//(b)

x=0:0.1:20
y0=[0;1]
function dy=f(x,y)
dy(1)=y(2)
dy(2)=y(1)*cos(2*x)
endfunction
sol=ode(y0,x(1),x,f);
subplot(2,1,2)
plot(x,sol(1,:),'rx')
plot(x,sol(2,:),'kx')
xlabel('x','fontsize',3)
ylabel("y(x) and dy(x)/dx","fontsize",3)
title("Plot for ODE (b)","fontsize",3)
legend("y(x)","dy(x)/dx")

5
1.1.4 Example 4
//Find the root of x^3-10x^2+5=0 that lies in the interval of 0 to 1
//also plot the function
clc
n=100;
y=zeros(n)
x=0:0.01:1
root=zeros(2)
j=1;
function y=f(x)
y=x^3-10*x^2+5
endfunction
for i=1:length(x)
if((abs(f(x(i)))<0.1)&&(abs(f(x(i+1)))>=0.1))
root(j)=x(i);
j=j+1;
end
end
disp(root)
plot(x,f(x))
plot(root,f(root),'k.')
xlabel('x','fontsize',3)
ylabel('y(x)','fontsize',3)
legend('y(x)','roots of y(x) between 0 and 1 is '+string(root))
title('Plot of y(x) and its root ','fontsize',3)

6
1.1.5 Example 5
//A skydiver of mass m in a vertical free fall experiences an aerodynamic
//drag force CD*y'^2 where y is measured downward from the start of the fall.
//The differential equation describing the fall is y"=-g-CD/m*y^2
//Determine the time of a 500m fall
clc
g=9.8;
CD=0.2028;
m=80;
t=0:0.01:18
y0=[500;0]
function dy=f(x,y)
dy(1)=y(2)
dy(2)=-g+(CD*(y(2)*y(2)))/m
endfunction
sol=ode(y0,0,t,f)
y=sol(1,:)
dy=sol(2,:)
time=0;
for i=1:length(y)

7
if(abs(y(i))<0.1)
time=i
break
end
end
j=time*0.01
plot(t,y)
plot(t,dy,'r')
plot(t(time),y(time),'r.')
xlabel('time(s)','fontsize',3)
ylabel('height,y(m) and velocity,dy/dt(m/s)','fontsize',3)
title('Plot for body under drag force','fontsize',3)
legend('height of body','velocity of body','time of flight is '+string(j)+'s')
xgrid();

8
Chapter 2

Shooting Method (to solve boundary


value problems)

Boundary value problems (BVPs) are second order differential equations whose solutions
at two values of the independent variable (boundaries) are given, instead of the values
of the dependent variable and its first derivative, as is given in an initial value problem.
Hence the name boundary value problem. This complicates the method to obtain a
solution of a BVP since the inbuilt functions in python, scipy or scilab are designed to
solve differential equations when the initial conditions are only given (There are however
higher level functions in scilab for solving BVPs).
Here we will discuss methods to solve BVPs using the inbuilt functions in scilab for
solving initial value problems. To do this we need to use a method, aptly called the
shooting method. The idea is to use the known solution of the BVP at one boundary and
an initial guess of its first derivative at that point and solve the ode to find the solution
at the other boundary. This value is then compared to the known solution of the BVP
at the other boundary. If it matches (you would be lucky, if it does) then you have got
the solution, else you have to go back and guess another value for the first derivative,
depending upon whether the solution at the second boundary undershot or overshot the
known boundary value. This will be repeated until your solution matches the boundary
value. This is akin to an archer trying to shoot an apple from a distant tree. Her first
try might fail, from which she will learn and change her aim the second time and again
till she succeeds. It also is similar to a gunner trying to shoot a cannon so that it hits
the target (see figure 2.1). The aim has to be adjusted by trial and error till the aim is
correct for hitting the target. This in essence is the shooting method of solving boundary
value problems.
To illustrate the shooting method of solving a BVP, let us consider the following boundary
value problem with the boundary values as given below

d2 y dy
+ + y = sin(3x) (2.1)
dx2 dx
y(0) = 1; (2.2)
y(5) = −1. (2.3)

9
Figure 2.1: Illustration of the shooting method. A cannon’s aim has to be adjusted by
trial and error till the aim is right to hit the target. Similarly in solving a BVP, the
first derivative of a second order ode has to be adjusted till the value is just right for the
solution to hit the correct value at the other boundary. The figure is taken from the book
[2].

To proceed with the solution using shooting method, first two guesses of the first derivative
of y have to be given. Moreover the two initial values of the first derivative have to be
such that one overshoots while the other undershoots the second boundary value. In
other words, the difference between the value of each of the two solutions at the second
boundary and the boundary value should be of opposite signs. This will ensure that the
correct value of the first derivative at the first boundary will definitely lie between these
two initial guesses and we can arrive at this value using the well known bisection method.
So this implementation of the shooting method uses the bisection method to arrive at the
correct value of the first derivative which will give the solution to our BVP. Once we have
the two initial guesses, we solve the ode with these first derivative guesses. Then we find
the middle value of this interval and solve the ode again taking this as the value of the
first derivative. Once the solution is known, we find the value at the second boundary
and take its difference with the actual boundary value. We then replace one of the initial
guesses of the first derivative with the middle value. That initial guess is replaced whose
solution at the second boundary differs from second boundary condition with the same
sign as the solution with the middle value as the first derivative guess. This is repeated
until the interval between the two guesses of the first derivative does not become smaller
than the accuracy we desire for the correct first derivative value. Once the interval has
become smaller we can solve the ode with the last middle value; this will give the solution
which will match the given boundary values within the decided accuracy.

2.0.1 Programme
The following code solves the BVP given in equation 2.3.
// Solve the 2nd order BVP defined by the ode d2y/dx2 + dy/dx + y = sin(3x)
// y(0) = 1 y(5) = -1
// using bisection method

function D_y = f(x,y)


D_y(1) = y(2)
D_y(2) = sin(3*x) - y(1) - y(2)
endfunction
x = linspace(0,5,100)

10
alpha_1 = -1e4
alpha_2 = 1e7
tolerance = 1e-5
gap = abs(alpha_1 - alpha_2)
i = 1
while gap > tolerance
//disp("while")
y0 = [1;alpha_1]
solution = ode(y0,0,x,f)
y_b = solution(1,$)
difference_1 = y_b - (-1)
//disp('diff 1 is',difference_1)
y0 = [1;alpha_2]
solution = ode(y0,0,x,f)
y_b = solution(1,$)
difference_2 = y_b - (-1)
//disp('diff 2 is',difference_2)
if (difference_1*difference_2) > 0
disp("choose proper interval")
break
end
alpha_mid = (alpha_1+alpha_2)/2
y0 = [1;alpha_mid]
solution = ode(y0,0,x,f)
y_b = solution(1,$)
difference_mid = y_b - (-1)
//disp('diff mid is',difference_mid)
//disp(difference_1*difference_mid)
if difference_1*difference_mid < 0 then
alpha_2 = alpha_mid
//disp("lower")
else
alpha_1 = alpha_mid
//disp('upper')
end
gap = abs(alpha_1 - alpha_2)
disp('gap is',gap)
disp(i)
i = i + 1
//disp('alpha_mid is',alpha_mid)
end
y0= [1;alpha_mid]
final_solution = ode(y0,0,x,f)
y_final = final_solution(1,:)
plot(x,y_final)
plot([0,5],[-1,-1],'k')

11
7

−1

−2
0 0.5 1 1.5 2 2.5 3 3.5 4 4.5 5

Figure 2.2: The solution to BVP in equation 2.3.

2.0.2 Output
The plot of the resulting solution is given in figure 2.2.

2.0.3 Using inbuilt root solver function


The same problem can be solved using the root finding function ’fsolve’ in scilab instead
of writing the code for the bisection method. However a function has to be defined whose
root will be found by the ’fsolve’ function. This function is basically the difference of the
solution at the second boundary for any given value of the first derivative with that of
the second boundary condition. A code for solving the BVP in equation 2.3 using ’fsolve’
is given below.
// Solve the 2nd order BVP defined by the ode d2y/dx2 + dy/dx + y = sin(3x)
// y(0) = 1 y(5) = -1

function D_y = f(x,y)


D_y(1) = y(2)
D_y(2) = sin(3*x) - y(1) - y(2)
endfunction
x = linspace(0,5,100)
function difference = g(alpha,x)

12
y0 =[1;alpha]
solution = ode(y0,0,x,f)
difference = solution(1,$)-(-1)
endfunction
alpha_optimum = fsolve(1,g)
y0 = [1;alpha_optimum]
final_sol = ode(y0,0,x,f)
plot(x,final_sol(1,:),'c')
plot([0,5],[-1,-1],'k')

d2 y dy
2
+ 5 + y = cos(x) (2.4)
dx dx
y(1) = 0.5; (2.5)
0
y (2) = −1.5. (2.6)

Another BVP problem defined in equation 2.6 can be solved using the code given below.
Note that the second boundary value specifies the first derivative at the second boundary.
The solution is plotted in figure 2.3.
/* SOLVE THE BOUNDARY VALUE PROBLEM (BVP) DESCRIBED BY THE ORDINARY
DIFFERENTIAL EQUATION D2Y/DX2 + 5(DY/DX) + Y = COS(X) */
// Y(1) = 0.5 Y'(2) = -1.5
function D_y = f(x,y)
D_y(1) = y(2)
D_y(2) = cos(x)-5*y(2)-y(1)
endfunction

x = linspace(1,2,100)
function difference = g(alpha)
y0 = [0.5;alpha]
solution = ode(y0,1,x,f)
difference = solution(2,$) - (-1.5)
endfunction
optimum_alpha = fsolve(0.5,g)
y0 = [0.5;optimum_alpha]
final_sol = ode(y0,1,x,f)
plot(x,final_sol(1,:))
//plot(x,final_sol(2,:))
plot([1,2],[7,7],'k')
xs2eps(0,'Plot_BVP_1')

13
10

0
1 1.1 1.2 1.3 1.4 1.5 1.6 1.7 1.8 1.9 2

Figure 2.3: The plot of the solution to BVP in equation 2.6.

14
Chapter 3

Shooting Method for Schrodinger


Equation

In this chapter, we will solve the Schrodinger equation for a finite potential well using the
shooting method. For a more detailed reading the user is referred to the book by Moruzzi
[3]
The finite well is given by (
0 if |x| <x0 ,
V = (3.1)
V0 if |x| > x0 .
The time independent Schrodinger equation for the finite well potential can be written
as
~2 d2 ψn (x)
− = En ψn (x), for |x| < x0 (3.2)
2m dx2
~2 d2 ψn (x)
− + V0 ψn (x) = Eψn (x), for |x| > x0 . (3.3)
2m dx2

We can√convert this equation in terms√of an dimensionless variable ξ = x/α where


α = ~/ 2mV0 . Thus, ξ0 = x0 /α = x0 2mV0 /~ is the strength of the potential well.
[4] Further introducing the dimensionless variable Wn = En /V0 , the equations 3.3 be-
come
d2 ψ(ξ)
= −Wn ψ(ξ), for |ξ| <ξ0 (3.4)
dξ 2
d2 ψ(ξ)
= (1 − Wn )ψ(ξ), for |ξ| >ξ0 . (3.5)
dξ 2

The finite square well has bound states for En < V0 or Wn < 1. Since the wave function
ψn (ξ) is zero far away outside the finite well, hence the second order equations given by
equation 3.5 represents a boundary value problem.
We solve this with a slightly modified shooting method, where instead of finding the
appropriate initial condition (e.g. the first derivative at the initial point) which will give
the proper solution satisfying the boundary condition (i.e. ψ(ξ) disappears at |ξ| >> ξ0 ),
we find the values of energy or what is the same thing i.e. Wn which will lead to the

15
solutions to the boundary value problem. These energies are the energy eigenvalues Wn
(En ).
To do this, we use the fact that the solutions for energies other than the eigenvalues
diverge at large ξ i.e. far away from the boundaries of the finite well.
The algorithm for finding the wave-functions for the finite well is as follows:
1. We begin with an initial guess of the energy eigenvalue. Since energy is always
positive, we begin with Wn = 0.
2. The first eigenfunction will be even. So we set a variable which will count the
number of eigenvalues to zero. If the eigenfunction is even we choose ψ(ξ = 0) = 1
and dψ

(ξ = 0) = 0 and vice-versa if it is odd.
3. We begin a while loop which will search for the eigenvalues Wn in an incremental
manner as long as Wn < 1. The code firsts calculates the solution at the inital guess
of the eigenvalue. Then it finds the solution at a new energy value obtained by
adding the step in energy to the initial guess. It then checks whether they diverge
in opposite directions far away form the finite well boundary. This is repeated until
two values of energy are obtained for which the solutions diverge in opposite ways.
4. The two above values of energy bracket the energy which is our required eigenvalue
at which the solution does not diverge appreciably at large ξ. To find that we
start a while loop which calculates the midpoint of the above energy interval and
calculates the solution at this middle energy. It then compares how this solution
diverges at large ξ with the solutions for the energies of the endpoints of the interval.
The endpoint whose solution diverges in an opposite way to that for the midpoint
is chosen as the new interval along-with the midpoint. This is repeated until the
interval becomes smaller than a predetermined accuracy in energy.
5. Once the energy at which the solution does not diverge appreciably (eigenvalue)
has been found, we truncate the solution to a range of ξ for which we will plot the
solution (because even for the eigenvalue there is some divergence at large ξ). This
is our wave-function. But we normalize it by integrating square of the wave-function
and then dividing the unnormalized wave-function with the norm. We also scale
the wave-function by a suitable factor so that the different eigenfunctions are well
spaced out when we plot them. We also generate the wavefunctions for the negative
side of ξ using the proper symmetry conditions for even and odd functions.

3.0.1 Programme
The code for finding the eigenvalues and eigenfunctions is given below:
nPointsWell = 100 /*number of sampling points for the wavefunction
from x = 0 to x = xi0 */
nPoints = 500 /*number of sampling points for the wavefunction
from x = 0 to x = xiMax */
nPointsPlot = 200 /* number of sampling points for the wavefunction
from x = 0 to x = xiMaxPlot */
xi0 = 10 /*Half-width of the finite potential well in dimesionless
position variable x(x = $\epsilon$,see text) */

16
xiMax= (xi0*nPoints)/nPointsWell /*Highest x($\epsilon$) used for
calculation.*/
xiMaxPlot = (xi0*nPointsPlot)/nPointsWell /* Highest plotted
x($\epsilon$) value. */
EigvStep =0.05 /*Step size in the search for eigenvalues
()energy values for which there is a solution to the BVP or SE)
DeltaXi =xiMax/nPoints */
tolerance = 1.0e-12 /* the tolerance level of error in the
energy eigenvalue for which there is a solution */
s = ['r' 'g' 'b' 'c' 'm' 'y' 'k']/* string containing the keywords for
plotting each eigenfunction with a different colour */

xi = linspace(0,xiMax,nPoints) /* the row matrix or vector with


nPoints number of equally spaced values from x = 0 to x = xiMax
for calculating the wavefunctions */
function Dy = f(xi,y,E) /* defines the function f which returns the
derivative (y', i.e. Dy(1)) of y(i.e. y(1)) and derivative
(y'', i.e. Dy(2)) of y'(i.e., y(2)) */
if xi < xi0 then /* the SE inside the well
(only positive half) where potential is 0*/
Dy(1) = y(2)
Dy(2) = -E*y(1)
else /*the SE outside the well (postive half only)
where potential is V0 */
Dy(1) = y(2)
Dy(2) = (1-E)*y(1)
end
endfunction

n = 0 // counter for number of eigenstates (eigenvalues)


Eigen = [] /*matrix for storing the eigenvalues or energies
for which there is a solution */
E1 = 0 /*Value for energy from which search for eigenvalues
is to be searched. */
E = E1 /* sets E in the function f to E1 */
// enters the loop to find the eigenvalues
while E < 1 /* loop runs as long mfor E is less than 1can be 1 as
E < V0 for bound states */
if modulo(n,2) == 0 then
y0 = [1;0] // initial value y = 1 and y' = 0 for even states
else
y0 = [0;1] // initial value y = 0 and y' = 1 for odd states
end
psi = ode(y0,xi(1),xi,f) /* Finds once the solution to ode for the
inital conditions mentioned */
psi_end1 = psi(1,$) /* value of the solution at the end point
xiMax is found out */
/*this loop is to find the interval of energy values at

17
the ends of which the solution diverges in opposite ways
(positive or negative) */
while 2 >0
E2 = E1 + EigvStep /* Finds a new energy value by
incrementing the initial energy value */
E = E2 // Increments E by step size to next value
psi = ode(y0,0,xi,f) /* Solves ode for new energy value
and earlier initial conditions */
psi_end2 = psi(1,$) /*Finds the value of the solution at the
end point xiMax */
if psi_end1*psi_end2 <0 /* compares the solution at the end
point for the last energy with that for the second last energy value*/
disp('break') /* breaks from the loop to search for the
interval without updating E1 */
break
end
E1 = E2 // updates the initial energy value to the last one
psi_end1 = psi_end2 /* updates the solution of initial energy
to the last one */

end
if E1 > 1 then /* If E1 has reached 1 then break from
loop of searching for energy intervals otherwise it will calculate
for one energy value higher than 1. */
break
end /* search for the energy value for which there is a solution
similar to the bisection method */
while abs(E1-E2)> tolerance /*checks that the energy interval
is less than the tolerance */
E_m = (E1+E2)/2 // finds the midvalue of the interval
E = E_m
psi = ode(y0,0,xi,f) // finds solution at midvalue
psi_end3 = psi(1,$) // finds solution at end point
if psi_end3*psi_end1 < 0 then /* compares the solution at
endpoint for midvalue of energy with that of the lower limit of the
interval */
E2 = E_m /* if it has changed sign, then
replaces the upper limit with the midpoint */
psi_end2 = psi_end3
elseif psi_end3*psi_end2 < 0 then // else does the reverse
E1 = E_m
psi_end1 = psi_end3
end
end
wavefunction = psi(1,:) /* calls the solution for the midpoint
which is eigenvalue as the wavefunction */
while length(xi) > nPointsPlot /* this loop truncates xi row matrix
so that its range is only till xiMaxPlot */

18
xi($) = []/* replaces with null element for columns higher
than xiMaxPlot */
wavefunction($) = [] /*replaces with null element for columns
higher than xiMaxPlot */
end

Eigen($+1) = E_m /* Appends the latest midvalue of energy as


eigenvalue to the matrix of eigenvalues */
E = E_m + EigvStep /* Takes E to one increment away from the last
midvalue (Eigenvalue) otherwise it will again find the same midvalue*/
Norm_factor = sqrt(2*inttrap(xi,wavefunction**2)) /* integrate to
find the norm of the current wavefunction */
normalised_wf = wavefunction*0.25/Norm_factor /* normalizes the
wavefunction by dividing with norm and scales by a suitable value to
plot */
if modulo(n,2) == 0 then // if the counter is even
flip_wf = flipdim(normalised_wf,2) /*flips the wavefunction
matrix */
flip_wf($)=[] /* removes the last element
of flipped matrix so that x = 0 is not repeated when we
concatenate next (i.e. join two matrices) */
else
flip_wf = flipdim(-normalised_wf,2)//flips with a negative sign
flip_wf($)=[] //similarly removes last element
end
total_wf = cat(2,flip_wf,normalised_wf)+ E_m /* joins the +ve and
-ve sides of the wavefunction and adds value equal to the energy
eigenvalue */
flip_xi = flipdim(-xi,2)
flip_xi($) = []
total_xi = cat(2,flip_xi,xi) /* last three lines generate x from
-xiMaxPlot to +xiMaxPlot */
n = n + 1 // increments counter
disp('length of total_wf is',length(total_wf))
plot(total_xi,total_wf,s(n)) // plots the wavefunction
plot([total_xi(1),total_xi($)],[E_m,E_m],'k') /*plots horizontal
lines at each energy eigenvalue*/
end

disp(Eigen) // displays the matrix of eigenvalues


plot([total_xi(1),-xi0],[1,1],'r','LineWidth', 2)
plot([xi0,total_xi($)],[1,1],'r','LineWidth', 2)
plot([-xi0,-xi0],[1,0],'r','LineWidth', 2)
plot([xi0,xi0],[0,1],'r','LineWidth', 2)
plot([-xi0,xi0],[0,0],'r', 'LineWidth', 2) /*last 5 lines plot the
finite potential well outline */

title("Eigenvalues and eigenfunctions of finite square well","fontsize",5)

19
Eigenvalues and eigenfunctions of finite square well
1.2

1.1

0.9

0.8

0.7

0.6

0.5

0.4

0.3

0.2

0.1

0
−20 −15 −10 −5 0 5 10 15 20

Figure 3.1: The eigenfunctions plotted as a function of ξ for a finite potential well with
ξ0 = 10. The eigenfunctions are displaced by the energy eigenvalue for clarity.

// gives title to plot


xlabel("$\xi = \frac{x \sqrt{2mV_0}}{\hbar}$", "fontsize",4)
// writes the x-axis label
ylabel("$W = E/V_0$","fontsize",4) // writes the y-axis label
xgrid(1,1) // plots a grid
xs2eps(0,'Plot_of_finite_square_well') // generates a png file of the plot

3.0.2 Output
The results of running the code is shown in figure 3.1

3.0.3 Diverging of solutions


In the following code we plot the wavefunctions at energies slightly off from an eigenvalue
to show how these diverge at large ξ as compared to the eigenfunction. The code can
be changed for a suitable starting energy to choose a particular eigenfunction. Also the
range of ξ to be plotted can be changed to a suitable value. The result is plotted in figure
3.2
nPointsWell = 100
nPoints = 500

20
nPointsPlot = 200
xi0 = 10
xiMax= (xi0*nPoints)/nPointsWell
xiMaxPlot = (xi0*nPointsPlot)/nPointsWell
EigvStep =0.05
tolerance = 1.0e-12
s = ['r' 'g' 'b' 'c' 'm' 'y' 'k']
Delta_E = 1.0E-5
xi = linspace(0,xiMax,nPoints)
function Dy = f(xi,y,E)
if xi < xi0 then
Dy(1) = y(2)
Dy(2) = -E*y(1)
else
Dy(1) = y(2)
Dy(2) = (1-E)*y(1)
end
endfunction

n = 0
Eigen = []
E1 = 0.05 // Energy value from whgich search is to be started.
E = E1
// enters the loop to find the eigenvalues
if modulo(n,2) == 0 then
y0 = [1;0] // initial value y = 1 and y' = 0 for even states
else
y0 = [0;1] // initial value y = 0 and y' = 1 for odd states
end
psi = ode(y0,xi(1),xi,f)
psi_end1 = psi(1,$)
// this loop is to find the interval of energy values at the ends of
// which the solution diverges in opposite ways (positive or negative)
while 2 >0
E2 = E1 + EigvStep
E = E2
psi = ode(y0,0,xi,f)
psi_end2 = psi(1,$)
if psi_end1*psi_end2 <0
disp('break')
break
end
E1 = E2
psi_end1 = psi_end2

end
//search for the energy value for which there is a solution similar
//to the bisection method

21
while abs(E1-E2)> tolerance
E_m = (E1+E2)/2
E = E_m
psi = ode(y0,0,xi,f)
psi_end3 = psi(1,$)
if psi_end3*psi_end1 < 0 then
E2 = E_m
psi_end2 = psi_end3
elseif psi_end3*psi_end2 < 0 then
E1 = E_m
psi_end1 = psi_end3
end
end
wavefunction = psi(1,:)
E = E_m - Delta_E
psi_lower = ode(y0,0,xi,f)
E = E_m + Delta_E
psi_upper = ode(y0,0,xi,f)
plot(xi(1:nPointsPlot),psi(1,1:nPointsPlot),'go')
plot(xi(1:nPointsPlot),psi_lower(1,1:nPointsPlot),'r','LineWidth',4)
plot(xi(1:nPointsPlot),psi_upper(1,1:nPointsPlot),'b', 'LineWidth',2)
disp('psi_upper',psi_upper(1,$))
disp('psi_upper',psi_lower(1,$))
legend('$W_n$','$W_n - \Delta W$','$W_n + \Delta W$')

disp(Eigen)

title("$\text{Diverging solutions at large }\xi$", "fontsize", 5)


xlabel("$\xi = \frac{x \sqrt{2mV_0}}{\hbar}$", "fontsize",4)
ylabel("$W = E/V_0$","fontsize",4)
xgrid(1,1)
xs2eps(0,'Plot_of_diverging_solutions')

22
1

0.8

0.6

0.4

0.2

−0.2

−0.4

−0.6

−0.8

−1
0 2 4 6 8 10 12 14 16 18 20

Figure 3.2: The solutions diverge for energies slightly lower or higher than the eigenvalue
at large ξ

23
Chapter 4

The Harmonic Oscillator Problem

The harmonic oscillator problem can be solved similarly to the finite well method using
the shooting method and the fact that the eigenfunctions of harmonic oscillator decay to
zero far way from the centre of the potential at x = 0.
We start with the Schrodinger equation for the harmonic oscillator. The potential is given
as
V = 1/2mω 2 x2 (4.1)
and the Schrodinger equation as

~ 2 d2 ψ n 1
− 2
+ mω 2 x2 ψn = En ψn . (4.2)
2m dx 2

Multiplying all throughout by 2



we get

~ d2 ψn mωx2 2En
− 2
+ ψn = ψn . (4.3)
mω dx ~ ~ω

If we introduce the dimensionless variable ξ = αx and Wn = En /~ω such that α =


p mω
~
then the above equation becomes

d2 ψn
− + ξ 2 ψn = 2Wn ψn (4.4)
dξ 2

This can be rearranged to write as

d2 ψ n
= [ξ 2 − 2Wn ]ψn . (4.5)
dξ 2

We will use this equation to define the ode in our code. We can break the second order
differential equation in to a system of first order differential equation as follows
dψn
= χn (4.6)

dχn
= [ξ 2 − 2Wn ]ψn . (4.7)

24
4.0.1 Programme
The algortithm for finding the eigenvalues and eigenfunctions for the harmonic oscillator
are the same as that of finite well. One difference is that there is no upper limit to the
energy eigenvalue, so we need to set a limit on the number of eigenvalues to be calculated
for the harmonic oscillator. Below is the code for solving the Schrodinger equation for
the first seven eigenvalues and eigenfunctions of the harmonic oscillator.
nPoints = 500 // Total number of points in x used in the calculation
nPointsPlot = 200 // Number of points in x which are plotted
xiMax=10.0 /* The maxiumum value of $\xi$ used in the calculation.
It is assumed that the eigenfunctions will be almost zero at
$\xi_{max}$*/
xiMaxPlot = (xiMax*nPointsPlot)/nPoints // $xi$ upto which plotted
tolerance = 1.0e-12 // Size of error in eigenvalues.
nEigen = 7 // Number of eigenvalues to be found.
EigvStep = 0.005// Step size of energy while searching for eigenvalues
s = ['r' 'g' 'b' 'c' 'm' 'y' 'k'] // array of strings for plot colour

xi = linspace(0,xiMax,nPoints)/* Generates a row matrix for $\xi$ to


be used in calculation*/

function Dy = f(xi,y,E)// Defines the SE as a system of 1st order odes


Dy(1) = y(2)
Dy(2) = (xi*xi-2*E)*y(1)
endfunction

n = 0 // Starts a counter for eigenvalues


Eigen = [] // Initializes a row matrix for storing eigenvalues.
E1 = 0 // Sets the initial value of energy from which to start search
E = E1 //Sets the variable E in the ode to initial value chosen in #22
while n < nEigen // While n is less than maximum number of eigenvalues
if modulo(n,2) == 0 then /* choose proper initial condition of
$\psi$ and $\psi'$ depending on whether eigenfunction is odd or even*/
y0 = [1;0]
else
y0 = [0;1]
end
psi = ode(y0,0,xi,f) // solve ode for initial value of E
psi_end1 = psi(1,$) // The value of solution at $\xi_{max}$
while 2 >0 //starts a while loop with a always true condition
E2 = E1 + EigvStep /*Increment to a new energy from the
initial value*/
E = E2 // Set variable E to the new value
psi = ode(y0,0,xi,f) // Solve ode for new E value
psi_end2 = psi(1,$) /*Store the value at $\xi_{max}$ of new
solution */
if psi_end1*psi_end2 <0 /* If the old and new solution diverge
in opposite directions, break from while loop with the two

25
energy values, old and new, as the interval of energy
containing the required energy which is the eigenvalue. At
this energy the solution will not diverge at $\xi_{max}$ */
//disp('break')
break
end
psi_end1 = psi_end2 /* if two energy values with oppositely
diverging solutions has not been found, then replace old
energy with new energy and start over again by incrementing to
a third energy value */
E1 = E2
end
while abs(E1-E2)> tolerance /* do a while loop as long as energy
interval is not less than the desired accuracy in energy eigenvalue*/
E_m = (E1+E2)/2.0 // Find the midpoint of energy interval
E = E_m // Set the variable E to midpoint in energy
psi = ode(y0,0,xi,f) /*Solve ode for the energy value equal
to the midpoint in energy */
psi_end3 = psi(1,$) /* Store the solution for the midpoint in
energy interval at $\xi_{max}$ */
// mprintf("psi_end1 is %e \n",psi_end1)
// mprintf("psi_end2 is %e \n",psi_end2)
// mprintf("psi_end3 is %e \n",psi_end3)
if psi_end3*psi_end1 < 0 then /* Check which endpoint of the
energy interval has a solution diverging in opposite direction to the
solution at the midpoint energy. This endpoint along with the midpoint
will be the new interval of energy for repaeting the process*/
E2 = E_m /*psi_end2 = psi_end3 seems to be not required in
any three programs!!?*/
psi_end2 = psi_end3
elseif psi_end3*psi_end2 < 0 then
E1 = E_m //similarly here also!!?
psi_end1 = psi_end3
end
//mprintf("energy interval is %e \n",abs(E1-E2))
end
wavefunction = psi(1,:) /*Set wavefunction as the first row of the
solution for the energy midpoint which we take as the eignevalue
within the accuracy limits set by us*/
while length(xi) > nPointsPlot /* Truncate $xi$ and wavefunction to
within maximum $\xi$ to be plotted */
xi($) = []
wavefunction($) = []
end
Eigen($+1) = E_m /* Add the latest eigenvalue to the list
of eigenvalues */
E = E_m + EigvStep /* Set the new value of energy to last
eigenvalue plus step in eigenvalue search */

26
Norm_factor = sqrt(2*inttrap(xi,wavefunction**2)) /* integrate the
square of the wavefunction and take square root to find the norm*/
normalised_wf = wavefunction*0.4/Norm_factor /* Normalize the
wavefunctions by dividing by norm and scale by an appropriate
factor for clarity in plotting */
if modulo(n,2) == 0 then /* Generate the wavefunction for negative
$\xi$ by choosing suitable symmetry for even and off
wavefunctions*/
flip_wf = flipdim(normalised_wf,2)
flip_wf($)=[]
else
flip_wf = flipdim(-normalised_wf,2)
flip_wf($)=[]
end
total_wf = cat(2,flip_wf,normalised_wf)+ E_m /* combine the
positive and negative part of the wavefunctions and add the
corresponding eigenvalue to separate the wavefunctions
along the y axis */
flip_xi = flipdim(-xi,2) // flip the matrix $\xi$
flip_xi($) = [] /* Remove $xi = 0$ to avoid duplicate entries after
combining */
total_xi = cat(2,flip_xi,xi) // Combine -ve and +ve $\xi$
//disp(length(total_xi))
n = n + 1 // Increment the eigenvalue counter by 1

//disp(length(normalised_wf))
//disp(normalised_wf)
//disp('length of total_wf is',length(total_wf))
plot(total_xi,total_wf,s(n), 'linewidth',3) // Plot the wavefunction
plot([total_xi(1),total_xi($)],[E_m,E_m],'k')/* Plot horizontal
line at the eigenvalue */
end
disp(Eigen)
title("Eigenvalues and eigenfunctions of harmonic potential","fontsize", 5)
xlabel("$\xi = \sqrt\frac{\omega m}{\hbar}$", "fontsize",4)
ylabel("$W = E/\hbar$","fontsize",4)
y = 0.5*total_xi**2
plot(total_xi,y,'k')
xgrid(1,1)
xs2eps(0,'Plot_of_harmonic_potential') // saves plot as eps file

4.0.2 Output
The results are given in figure 4.1.

27
Eigenvalues and eigenfunctions of harmonic potential
8

0
−4 −3 −2 −1 0 1 2 3 4

Figure 4.1: First seven eigenfunctions and eigenvalues of the harmonic oscillator.

28
Diverging solutions of harmonic potential
1

0.8

0.6

0.4

0.2

−0.2

−0.4

−0.6

−0.8

−1
0 0.5 1 1.5 2 2.5 3 3.5 4 4.5 5 5.5 6

Figure 4.2: Diverging solutions of the harmonic oscillator for energies deviating from the
eigenvalue.

4.0.3 Diverging of solutions


Similar to the finite well we can show that the solutions to the Schrodinger equation for
energies deviating from the eigenvalues blow up to ± ∞ at large values of ξ.
To do this we basically start searching for the eigenvalue near the vicinity of any eigenvalue
(for e.g. 0.5,1.5, 2.5, etc) and once the eigenvalue is found, we find the solutions at
Wn ± ∆W and plot the along with the eigenfunction to see if they diverge. The solutions
for energies below and above the eigenvalue will diverge in opposite directions as the
solution crosses zero for the energy equal to the eigenvalue. This is illustrated in figure
4.2. This method of finding the eigenfunctions is also known as the wag the tail method
[4]. The code for computing and plotting the same is given below.
nPoints = 500 // Total number of points in x used in the calculation
nPointsPlot = 300 // Number of points in x which are plotted
xiMax=10.0 /* The maxiumum value of $\xi$ used in the calculation.
It is assumed that the eigenfunctions will be almost zero at
$\xi_{max}$*/
xiMaxPlot = (xiMax*nPointsPlot)/nPoints // $xi$ upto which plotted
tolerance = 1.0e-12 // Size of error in eigenvalues.
EigvStep = 0.005// Step size of energy while searching for eigenvalues
Delta_E = 1e-7

29
xi = linspace(0,xiMax,nPoints)/* Generates a row matrix for $\xi$ to
be used in calculation*/

function Dy = f(xi,y,E)// Defines the SE as a system of 1st order odes


Dy(1) = y(2)
Dy(2) = (xi*xi-2*E)*y(1)
endfunction
n = 0 // Parity for odd or even states
E1 = 0 /* Sets the initial value of energy near the vicinity of the
eigenvalue around which we are exploring the solutions */
E = E1 //Sets the variable E in the ode to initial value chosen in #22

if modulo(n,2) == 0 then /* choose proper initial condition of


$\psi$ and $\psi'$ depending on whether eigenfunction is odd or even*/
y0 = [1;0]
else
y0 = [0;1]
end
psi = ode(y0,0,xi,f) // solve ode for initial value of E
psi_end1 = psi(1,$) // The value of solution at $\xi_{max}$
while 2 >0 //starts a while loop with a always true condition
E2 = E1 + EigvStep /*Increment to a new energy from the
initial value*/
E = E2 // Set variable E to the new value
psi = ode(y0,0,xi,f) // Solve ode for new E value
psi_end2 = psi(1,$) /*Store the value at $\xi_{max}$ of new
solution */
if psi_end1*psi_end2 <0
/* If the old and new solution diverge
in opposite directions, break from while loop with the two
energy values, old and new, as the interval of energy
containing the required energy which is the eigenvalue. At
this energy the solution will not diverge at $\xi_{max}$ */
disp('break')
break
end
psi_end1 = psi_end2 /* if two energy values with oppositely
diverging solutions has not been found, then replace old
energy with new energy and start over again by incrementing to
a third energy value */
E1 = E2
end
while abs(E1-E2)> tolerance
/* do a while loop as long as energy
interval is not less than the desired accuracy in energy eigenvalue*/
E_m = (E1+E2)/2 // Find the midpoint of energy interval
E = E_m // Set the variable E to midpoint in energy

30
psi = ode(y0,0,xi,f) /*Solve ode for the energy value equal
to the midpoint in energy */
psi_end3 = psi(1,$) /* Store the solution for the midpoint in
energy interval at $\xi_{max}$ */
if psi_end3*psi_end1 < 0 then
/* Check which endpoint of the
energy interval has a solution diverging in opposite direction to the
solution at the midpoint energy. This endpoint along with the midpoint
will be the new interval of energy for repaeting the process*/
E2 = E_m /*psi_end2 = psi_end3 seems to be not required in
any three programs!!?*/
elseif psi_end3*psi_end2 < 0 then
E1 = E_m //similarly here also!!?
end
end
E = E_m - Delta_E
psi_lower = ode(y0,0,xi,f)
E = E_m + Delta_E
psi_upper = ode(y0,0,xi,f)
plot(xi(1:nPointsPlot),psi(1,1:nPointsPlot),'go') // plots the wavefunction
plot(xi(1:nPointsPlot),psi_lower(1,1:nPointsPlot),'r','LineWidth',4)
plot(xi(1:nPointsPlot),psi_upper(1,1:nPointsPlot),'b', 'LineWidth',2)
disp('psi_upper',psi_upper(1,$))
disp('psi_upper',psi_lower(1,$))
legend('$W_n$','$W_n - \Delta W$','$W_n + \Delta W$')

title("Diverging solutions of harmonic potential", "fontsize", 5)


xlabel("$\xi = \sqrt\frac{\omega m}{\hbar}$", "fontsize",4)
ylabel("$W = E/\hbar$","fontsize",4)
//y = 0.5*total_xi(1:nPointsPlot)**2
//plot(xi(1:nPointsPlot),y,'k')
xgrid(1,1)
xs2eps(0,'Plot_of_diverging solutions of harmonic_potential')

31
Chapter 5

Radial Schrodinger equation: Hydrogen


atom

In case of a central potential where the potential only depends on the radial distance from
origin, the three dimensional Schrodinger equation can be separated into a radial and an
angular part [4]. The radial equation then can be written as

d 2 dR 2mr2
(r ) − 2 [V (r) − E]R = l(l + 1)R. (5.1)
dr dr ~
This equation can be simplified by changing the variables to

u(R) = rR(r). (5.2)

The equation after simplification becomes


~2 d2 u ~2 l(l + 1)
− + [V + ]u = Eu. (5.3)
2m dr2 2m r2
The normalization condition for the radial part of the wavefunction is
ˆ ∞ ˆ ∞
2 2
R r dr = u2 dr = 1, (5.4)
0 0

To solve the Hydrogen atom problem, we replace the potential V(r) with the coulomb
potential
e2
V (r) = − (5.5)
4π0 r
and the radial equation becomes
~2 d2 u e2 ~2 l(l + 1)
− + [− + ]u = Eu. (5.6)
2m dr2 4π0 r 2m r2
This equation can be converted to one in terms of a dimensionless variable ξ by the
substitution r = aξ where a is a constant with dimension of length and whose significance
we will see below. With this substitution the radial equation becomes
~ 2 d2 u e2 ~2 l(l + 1)
− + [− + ]u = Eu. (5.7)
2ma2 dξ 2 4π0 aξ 2ma2 ξ 2

32
~2
Now, 2ma2
has the dimension of energy and if we divide throughout by it, we have

d2 u 2mae2 l(l + 1) E
− 2
+ [− 2
+ 2
]u = ~2 u. (5.8)
dξ 4π0 ~ ξ ξ 2ma2

Introducing the dimensionless variable  = E


~2
we have
2ma2

d2 u 2mae2 l(l + 1)
− + [− + ]u = u. (5.9)
dξ 2 4π0 ~2 ξ ξ2
4π0 ~2
If we now choose a = me2
then the radial equation is simplified to a dimensionless form

d2 u 2 l(l + 1)
− + [− + ]u = u. (5.10)
dξ 2 ξ ξ2
4π0 ~2
The constant a = me2
is called the Bohr radius.  is energy in Rydberg since 1Rydberg =
~2 2 2
2ma2
= m
( e ).
2~2 4π0
The radial equation is now in a dimensionless form ready to be solved
computationally.
We use a similar procedure of the shooting method which we have used in previous
chapters to solve the radial equation for the hydrogen atom. However, if we shoot from
the origin (r = 0), then the solutions diverge at large r even for the eigenvalues. This is
illustrated in figure 5.1 for the energy eigenvalue 1 = −1 and l = 0. Hence we shoot from
large r or what is the same thing, large ξ and try to find energies for which the solution
at origin is zero. This is shown in figure 5.2 for the energy eigenvalue 1 = −1 and l = 0.

We know that the eigenvalues of energy of the hydrogen atom, in units of Rydberg, go
like n = 1/n2 where n = 1, 2, 3, ... . So while shooting, we start from energy values less
than 1 , for example -1.2 and go to higher energy values. We also use a logarithmically
spaced mesh for ξ since the higher wavefunctions extend out to larger distances.

5.0.1 Programme
The code for finding the first seven states for the l = 0 case is given below. The centrifugal
term in equation 5.10 is then zero. The procedure is similar to the earlier shooting methods
used except for the differences pointed out in the preceding paragraphs. The explanation
for the code is given in the comments.
r = logspace(-10,2,600) /* defines a logarithmic grid for radial
coordinate, note r = 0 is not taken instead r is taken to be a
very small value*/
r_flip = flipdim(r,2) /*flip the r matrix so that the first element is
the largest r */
function D_u = f(r,u,E) /* defines the system of first order ode
for the radial Schrodinger equation*/
D_u(1) = u(2)
D_u(2) = (-E-2/r)*u(1)
endfunction

33
0.4

0.35

0.3

0.25

0.2

0.15

0.1

0.05

0
0 2 4 6 8 10 12 14 16 18 20

Figure 5.1: Plot of eigenfunction for n = 1, l = 0 when shooting from origin.

u_0 = [0;1e-5] /* takes an initial value for the wavefunction and its
derivative */

E_0 = -1.2 // starting value of energy for search


E_tol = 1.0e-12 // accuracy to which the eigenvalue will be found
E_step = 0.005 // Step size of increment in energy for search

E1 = E_0 // Sets E1 to E_0


Eigen_list = [] // Initializes a list for storing eigenvalues
n_eigen = 1 // Starts a counter for the eigenfunction
s = ['r' 'g' 'b' 'c' 'm' 'y' 'k'] // list of string for plot

while n_eigen < 8 // starts a loop to search for eigenvalues


disp('n_eigen is',n_eigen)
E = E1 // Sets E in the ode to E1
u = ode(u_0,r_flip(1),r_flip,f) // solves the ode for E1
u_end1 = u(1,$) // finds the solution at origin (last element)
while 2 > 0 // starts loop to find the energy interval
E2 = E1 + E_step // increments to a new energy level
E = E2 // Sets E to the new value E2
u = ode(u_0,r_flip(1),r_flip,f) // Solves ode for E2

34
0.8

0.7

0.6

0.5

0.4

0.3

0.2

0.1

−0.1
0 10 20 30 40 50 60 70 80 90 100

Figure 5.2: Plot of eigenfunction for n = 1, l = 0 when shooting from large ξ.

u_end2 = u(1,$)// Finds the last element or solution at origin


disp("E2 is", E2)
if u_end1*u_end2<0 then
break /* if the solutions diverge in opposite directions
stop the search*/
disp("Range of eigenvalue found")
end
E1 = E2 /* if not update lower energy limit to the higher
energy limit */
disp("E1 is", E1)
u_end1 = u_end2 /* change the solution at the orgin for
the lower limit*/
end
disp("E1 is", E1)// displays the energy interval lower limit
disp("E2 is", E2)// displays the energy interval higher limit
while abs(E1-E2) > E_tol // search by bisection the eigenvalue
E_mid = (E1+E2)/2 // find the middle of the nergy interval
E = E_mid // Set E to this value
//disp("E_mid is", E_mid)
u = ode(u_0,r_flip(1),r_flip,f) // solve ode for E_mid
u_end3 = u(1,$) // find the solution at origin for E_mid

35
if u_end1*u_end3<0 then /* choose the proper limit based on
whether the lower or upper energy limit has a solution diverging in
opposite direction to the solution at the middle energy */
E2 = E_mid
u_end2 = u_end3
else
E1 = E_mid
u_end1 = u_end3
end
end /* break from loop when the energy interval is less than
the tolerance */
disp("E_mid, the new eigenvalue is", E_mid)
Eigen_list($+1) = E_mid // stores the E_mid as eigenvalue
n_eigen = n_eigen + 1 // icrements the eigenfunction counter
E1 = E_mid + E_step /* changes E1 in line# 19 to new energy to
nudge it to next root */
u_wf = flipdim(u(1,:),2) /*flips the solution to get wavefunction
in increasing r*/
disp("length of u_wf", length(u_wf))
disp("length of r", length(r))
norm_factor = sqrt(inttrap(r,u_wf**2))// normalization constant
u_wf = u_wf/norm_factor // normalize the wavefunction
plot(r,u_wf**2,s(n_eigen-1),'linewidth',3) /*plot square of the
eigenfunctions */
end
plot([r(1),r($)],[0,0],'k') // plot horizontal line
xs2eps(0,'Plot_of_hydrogen_atom_radial_wavefunctions') /*generates a
eps file of the plot */
disp(Eigen_list)

5.0.2 Output
The plot of the first seven radial s-wavefunctions are given in figure 5.3.

36
0.6

0.55

0.5

0.45

0.4

0.35

0.3

0.25

0.2

0.15

0.1

0.05

0
0 5 10 15 20 25 30 35 40 45 50 55 60 65 70 75 80 85 90 95 100

Figure 5.3: First seven radial s-wavefunctions for the Hydrogen atom.

37
Chapter 6

The Anharmonic Oscillator Problem

We are now going to solve the s-wave (l = 0) radial Schrodinger equation for a particle
of mass m in the anharmonic oscillator potential
1 1
V (r) = kr2 + br3 (6.1)
2 3
Here k = 100 MeV/f m2 , m = 940 MeV/c2 , b = 10 MeV/f m3 and c~ = 197.3 MeV-fm.
Setting c = 1, the radial part of schrodinger equation becomes

~2 d2 ψn
 
1 2 1 3
− + kx + bx ψn = En ψn (6.2)
2m dr2 2 3
q
Further setting ξ = r mk~2 transforms the Schrodinger’s equation as

 23 !
d2 ψn ~2 2 2b ~2

− 2 + ξ + ξ 3 ψn = Wn ψn . (6.3)
dξ mk 3k mk

2En
where Wn = k

We now use shooting method to numerically solve equation 6.3.


It should be mentioned that equation 6.3 cannot be solved analytically with-
out approximation methods such as perturbation theory or WKB approx-
imation. We ’shoot’ various trajectories and select the one that is closest
to the physical situation relevant here provided we have some initial condi-
tions.
How does one select the initial conditions? Well for starters it’s not rocket
science (It’s quantum mechanics so much more harder!). We do exactly what
one does while solving the classical harmonic oscillator. But why does the
harmonic oscillator’s fingerprints appear all over this?

38
Here’s why: if you have a force that causes a slight perturbation to a spring
system and this force is conservative then small oscillations about the mean
position can be described as:
∂V 1 ∂ 2V 1 ∂ 3V
V (r) = V (r0 )+( )|r=r0 (r−r0 )+ ( 2 )|r=r0 (r−r0 )2 + ( 3 )|r=r0 (r−r0 )3 +...
∂r 2! ∂r 3! ∂r
(6.4)
∂2V ∂3V
Now by setting ( ∂r2 )r=r0 = k(spring constant) and ( ∂r3 )r=r0 = b equation
6.4 becomes
1 1
V (r) = kx2 + bx3 .
2 6
The first derivative in equation 6.4 is zero as points of equilibrium tend to be
extremas. Below is the code for solving the anharmonic oscillator potential.
Figure 6.1 is the plot of the eigenfunctions of the anharmonic potential.
clc
nPoints = 500 //number of sampling points for the wavefunction
nPointsPlot = 200 // Number of points in x which are plotted
xiMax=10.0 //maximum value of x
xiMaxPlot = (xiMax*nPointsPlot)/nPoints//value of x upto which plotted
tolerance = 1.0e-12 //setting the tolerance for the values
nEigen = 7 //number of eigenstates plotted
EigvStep = 0.005 //step size for progression between eigenvalues
s = ['r' 'g' 'b' 'c' 'm' 'y' 'k']
xi = linspace(0,xiMax,nPoints) //defining x-axis points
m = 940 // mass of particle
k = 100 // spring constant
h =197.3 // Planck's constant
b = 10 // coefficient of cubic contribution
q1 = (h^2)/(m*k) //defining charecterstic scales
q2 = 2*m*b/(3*h.^2)
q3 = 2*m./h.^2
q4 = (2/3)*(b/k)*(h^2/(m*k))^(3/2)
function Dy = f(xi,y,E)//setting up the ODE for Schrodinger's equation
Dy(1) = y(2)
Dy(2) = (q1*xi*xi+q4*xi*xi*xi-E)*y(1)
endfunction
n = 0
Eigen = [] //defines empty array to store eigenvalues
E1 = 0 //initial guess W_n = 0
E = E1//Sets E to initial value chosen

39
while n < 7
if modulo(n,2) == 0
then
y0 = [1;0] // even solution
else
y0 = [0;1] // odd solution
end
psi = ode(y0,0,xi,f) //solving the ode given initial conditions
psi_end1 = psi(1,$) // value at xi_{max}
while 2 >0
E2 = E1 + EigvStep //finding the second eigenvalue
E = E2 //setting E in the ode equal to the 2nd eigenvalue
psi = ode(y0,0,xi,f) //solving the ode for 2nd energy
psi_end2 = psi(1,$) //xi_{max} for this eigenstate
if psi_end1*psi_end2 <0 /*incase there's a divergence break the loop
since we've obtained two different energy states*/
break
end
psi_end1 = psi_end2 /*if that's not the case then change your
eigenstate and repeat the process*/
E1 = E2
end
while abs(E1-E2)> tolerance /*Our two energy eigenvalues must differ
by not less than the set "tolerance value"*/
E_m = (E1+E2)/2.0 //find the midpoint of two energies
E = E_m //set the E parameter of ode equal to midpoint value
psi = ode(y0,0,xi,f) //solve the ode for midpoint value
psi_end3 = psi(1,$) //xi_{max} for this wavefunction

if psi_end3*psi_end1 < 0 /* Check which endpoint of the energy


interval has a solution diverging in opposite direction to the
solution at the midpoint energy. This endpoint along with the mid
point will be the new interval of energy for repeating the process*/
E2 = E_m
psi_end2 = psi_end3
elseif psi_end3*psi_end2 < 0
then
E1 = E_m
psi_end1 = psi_end3

40
end

end
wavefunction = psi(1,:) //Wavefunction is the first row
while length(xi) > nPointsPlot //truncation of wavefunction
xi($) = []
wavefunction($) = []
end
Eigen($+1) = E_m //setting the eigenvalues equal to the E values
E = E_m + EigvStep
Norm_factor = sqrt(2*inttrap(xi,wavefunction**2))//norm
normalised_wf = wavefunction*0.4/Norm_factor // normalization
if modulo(n,2) == 0 then /*setting a symmetry for even and odd
wavefunctions*/
flip_wf = flipdim(normalised_wf,2) //even
flip_wf($)=[]
else
flip_wf = flipdim(-normalised_wf,2) //odd
flip_wf($)=[]
end
total_wf = cat(2,flip_wf,normalised_wf)+ E_m /*unification of even
and odd wavefunctions*/
flip_xi = flipdim(-xi,2)
flip_xi($) = []
total_xi = cat(2,flip_xi,xi) /*unification of $xi$ and $-xi$ and */

n = n + 1 //increment the counter

plot(total_xi,total_wf,s(n), 'linewidth',2) /*plot the wavefunction


so obtained by such steps*/
plot([total_xi(1),total_xi($)],[E_m,E_m],'k') /*plotting the
horizontal at each wavefunction*/
end
Eigent=Eigen*k/2 /*computes the actual energy eigenvalue from the
reduced eigenenergy used in solving the ode*/
disp("Reduced Energy eigenvalues are")
disp(Eigen)/*displays the reduced energy eigenvalues i.e $W_{n}$ */
disp("Energy eigenvalues are")
disp(Eigen*k/2) /*displays the actual energy eigenvalues*/

41
xset("font size",4)//sets the fontsize of text
xstring(-6,10, ' E7 = ' + string(Eigent(7)))/*displays the energy
eigenvalue against every eigenstate plot*/
xstring(-6,8, ' E6 = ' + string(Eigent(6)))
xstring(-6,6.5, ' E5 = ' + string(Eigent(5)))
xstring(-6,5, ' E4 = ' + string(Eigent(4)))
xstring(-6,3.5, ' E3 = ' + string(Eigent(3)))
xstring(-6,2, ' E2 = ' + string(Eigent(2)))
xstring(-6,0.5, ' E1 = ' + string(Eigent(1)))

title("Eigenvalues and eigenfunctions of anharmonic potential","fontsize",


xlabel("$\Large{\textbf{\xi = x\sqrt{\frac{m k}{\hbar^{2}}}}}$", "fontsize
ylabel("$\Large{\textbf{\psi(\xi)}}$","fontsize",4)/*labels y-axis*/
y = q1*total_xi^2+q4*total_xi^3
plot(total_xi,y,'k','linewidth',3)/*plots the potential spanning the domai
a=gca() ;
a.box="off";
a.data_bounds=[-6,0;6,11]; //sets bounds of x,y axis
xs2png(0,'Plot_of_anharmonic_oscillator')
These are the eigenfunctions of the anharmonic oscillator. Notice that the
potential seems longer at one end than the other. This is an example of a
potential without inversion symmetry upon flipping of x-axis.
Eigenvalues too seem to have unequal spacing and seem close to the harmonic
oscillator eigenvalues. However this is hardly a surprise since anyone who’s
studied an iota of perturbation theory know this to be true. Long story short
energies do have unequal spacing(increases with increasing energy) and the
perturbation to energy caused at lower energies is smaller and higher energies
are larger. Note the discontinuity at origin. Why does it happen? Let’s leave
it as an exercise to the reader.

42
Figure 6.1: Eigenfunctions and eigenvalues of the anharmonic oscillator potential. The
thick black solid line is the plot of the potential.

43
Chapter 7

Some More Potentials

7.1 Coulumb Screening

Solving the radial part of Schrodinger Equation


Schrodinger equation in spherical coordinate is composed of all three r θ & φ
but can be separated into radial and angular parts. For simplicity and ac-
cording to the need of the problem we restrict ourselves to radial equation
given by :
d 2 dR 2mr2
(r ) − 2 [V (r) − E]R = l(l + 1)R (7.1)
dr dr ~
which may be simplified further by taking u(R) = rR(r) :
~2 d2 u ~2 l(l + 1)
 
− + V + u = Eu (7.2)
2m dr2 2mr2
The Coulomb screened potential function V(r) is given by
e −r/α
V (r) = − e (7.3)
4π0 r
where α is multiple of Bohr Radius unit. The equation thus becomes
~2 d2 u e −r/α ~2 l(l + 1)
 
− + − e + u = Eu (7.4)
2m dr2 4π0 r 2mr2
This equation can be converted to one in terms of a dimensionless variable ξ
by the substitution r = aξ where a is Bohr Radius a constant with dimension
of length . With this substitution the radial equation becomes
~2 d2 u 2
 
e ~ l(l + 1)
− 2 2
+ − e−ξ/α + u = Eu (7.5)
2m a dξ 4π0 aξ 2ma2 ξ 2

44
~2
Now 2ma2 has the dimension of energy and if we divide throughout by it, we
have
d2 u
 
2 −ξ/α l(l + 1)
− 2+ − e + u = £u (7.6)
dξ ξ ξ2
2 2
where a = 4π 0~ ~
me2 is the Bohr Radius,£ is in Rydberg since 1 Rydberg = 2ma2 .
The radial equation is now in a dimensionless form ready to be solved com-
putationally. The following code was run to get the required output as shown
below. α = 2 was taken as the value parameter.

7.1.1 Programme
for l=0:1:1
scf(l)
r = logspace(-10,2,600)
r_flip = flipdim(r,2)
function D_u=f(r, u, E)
D_u(1) = u(2)
D_u(2) = ((-E-2/r)*exp(-r/2)+(l*(l+1)/r**2))*u(1)
endfunction
u_0 = [0;1e-5]
E_0 = -1.2
E_tol = 1.0e-12
E_step = 0.05
E1 = E_0
Eigen_list = []
n_eigen = 1
s=['red','maroon','magenta','purple','plum','violet','darkorchid','blue','cyan',
'turquoise','limegreen','forestgreen','green','yellow','orange','brown']
while n_eigen < 17
E = E1
u = ode(u_0,r_flip(1),r_flip,f)
u_end1 = u(1,$)
while 2>0
E2 = E1 + E_step
E = E2
u = ode(u_0,r_flip(1),r_flip,f)
u_end2 = u(1,$)
if u_end1*u_end2<0 then
break
end
E1 = E2
u_end1 = u_end2
end
while abs(E1-E2) > E_tol
E_mid = (E1+E2)/2
E = E_mid
u = ode(u_0,r_flip(1),r_flip,f)
u_end3 = u(1,$)

45
if u_end1*u_end3<0 then
E2 = E_mid
u_end2 = u_end3
else
E1 = E_mid
u_end1 = u_end3
end
end
Eigen_list($+1) = E_mid
n_eigen = n_eigen + 1
E1 = E_mid + E_step
u_wf = flipdim(u(1,:),2)
norm_factor = sqrt(inttrap(r,u_wf**2))
u_wf = u_wf/norm_factor
plot2d(r,u_wf**2,style=color(s(n_eigen-1)))
gca().font_size=4;
xstring((n_eigen-1)*6-6,.07+(l*.05)-(.002*n_eigen+(l*.005)),"${\textcolor{"+s(n_eigen-1)+
"}{\text{\epsilon_{"+string(n_eigen-1)+"}="+string(Eigen_list(n_eigen-1))+"}}$")
title("$Eigenfunctions\ at\ l\ ="+string(l)+"$", "fontsize", 5.5)
xlabel("$\xi = r\frac{me^2}{4\pi\epsilon_0\hbar^2}=\frac{r}{R_B}$", "fontsize",5)
ylabel("$Radial\ Part\ \psi(r)$","fontsize",5)
end
end

7.1.2 Output

Figure 7.1: Eigenfunctions of screened coulomb potential for l = 0 case.

46
Figure 7.2: Eigenfunctions of screened coulomb potential for l = 1 case.

7.2 Double Well


7.2.1 Programme
nPoints = 500 // Total number of points in x used in the calculation
nPointsPlot = 200 // Number of points in x which are plotted
xiMax=10.0 /* The maxiumum value of $\xi$ used in the calculation.
It is assumed that the eigenfunctions will be almost zero at
'$\xi_{max}$'*/
xiMaxPlot = (xiMax*nPointsPlot)/nPoints // $xi$ upto which plotted
tolerance = 1.0e-12 // Size of error in eigenvalues.
nEigen = 9 // Number of eigenvalues to be found.
EigvStep = 1// Step size of energy while searching for eigenvalues
s = ['maroon' 'red' 'orange' 'limegreen' 'forestgreen' 'blue' 'turquoise' 'purple'
'darkorchid']// array of strings for plot colour
xi = linspace(0,xiMax,nPoints)/* Generates a row matrix for $\xi$ to
be used in calculation*/
function Dy = f(x,y,E)// Defines the SE as a system of 1st order odes
Dy(1) = y(2)
Dy(2) = ((2/2)*(x**2-4)**2-E)*y(1)
endfunction
n = 0 // Starts a counter for eigenvalues
Eigen = [] // Initializes a row matrix for storing eigenvalues.
E1 = 0 // Sets the initial value of energy from which to start search
E = E1 //Sets the variable E in the ode to initial value chosen in #22
while n < nEigen // While n is less than maximum number of eigenvalues
if modulo(n,2) == 0 then /* choose proper initial condition of $\psi$ and $\psi'$
depending on whether eigenfunction is odd or even*/
y0 = [1;0]
else

47
y0 = [0;1]
end
psi = ode(y0,0,xi,f) // solve ode for initial value of E
psi_end1 = psi(1,$) // The value of solution at $\xi_{max}$
while 2 >0 //starts a while loop with a always true condition
E2 = E1 + EigvStep /*Increment to a new energy from the
initial value*/
E = E2 // Set variable E to the new value
psi = ode(y0,0,xi,f) // Solve ode for new E value
psi_end2 = psi(1,$) /*Store the value at $\xi_{max}$ of new
solution */
if psi_end1*psi_end2 <0 /* If the old and new solution diverge
in opposite directions, break from while loop with the two
energy values, old and new, as the interval of energy
13
containing the required energy which is the eigenvalue. At
this energy the solution will not diverge at $\xi_{max}$ */
//disp('break')
break
end
psi_end1 = psi_end2 /* if two energy values with oppositely
diverging solutions has not been found, then replace old
energy with new energy and start over again by incrementing to
a third energy value */
E1 = E2
end
while abs(E1-E2)> tolerance /* do a while loop as long as energy
interval is not less than the desired accuracy in energy eigenvalue*/
E_m = (E1+E2)/2.0 // Find the midpoint of energy interval
E = E_m // Set the variable E to midpoint in energy
psi = ode(y0,0,xi,f) /*Solve ode for the energy value equal
to the midpoint in energy */
psi_end3 = psi(1,$) /* Store the solution for the midpoint in
energy interval at $\xi_{max}$ */
// mprintf("psi_end1 is %e \n",psi_end1)
// mprintf("psi_end2 is %e \n",psi_end2)
// mprintf("psi_end3 is %e \n",psi_end3)
if psi_end3*psi_end1 < 0 then /* Check which endpoint of the
energy interval has a solution diverging in opposite direction to the
solution at the midpoint energy. This endpoint along with the midpoint
will be the new interval of energy for repaeting the process*/
E2 = E_m /*psi_end2 = psi_end3 seems to be not required in
any three programs!!?*/
psi_end2 = psi_end3
elseif psi_end3*psi_end2 < 0 then
E1 = E_m //similarly here also!!?
psi_end1 = psi_end3
end
//mprintf("energy interval is %e \n",abs(E1-E2))
end
wavefunction = psi(1,:) /*Set wavefunction as the first row of the

48
solution for the energy midpoint which we take as the eignevalue
within the accuracy limits set by us*/
while length(xi) > nPointsPlot /* Truncate $xi$ and wavefunction to
within maximum $\xi$ to be plotted */
xi($) = []
wavefunction($) = []
end
Eigen($+1) = E_m /* Add the latest eigenvalue to the list
of eigenvalues */
E = E_m + EigvStep /* Set the new value of energy to last
eigenvalue plus step in eigenvalue search */
Norm_factor = sqrt(2*inttrap(xi,wavefunction**2)) /* integrate the
14
square of the wavefunction and take square root to find the norm*/
normalised_wf = wavefunction*0.4/Norm_factor /* Normalize the
wavefunctions by dividing by norm and scale by an appropriate
factor for clarity in plotting */
if modulo(n,2) == 0 then /* Generate the wavefunction for negative
$\xi$ by choosing suitable symmetry for even and off
wavefunctions*/
flip_wf = flipdim(normalised_wf,2)
flip_wf($)=[]
else
flip_wf = flipdim(-normalised_wf,2)
flip_wf($)=[]
end
total_wf = cat(2,flip_wf,normalised_wf)+ E_m /* combine the
positive and negative part of the wavefunctions and add the
corresponding eigenvalue to separate the wavefunctions
along the y axis */
flip_xi = flipdim(-xi,2) // flip the matrix $\xi$
flip_xi($) = [] /* Remove $xi = 0$ to avoid duplicate entries after
combining */
total_xi = cat(2,flip_xi,xi) // Combine -ve and +ve $\xi$
//disp(length(total_xi))
n = n + 1 // Increment the eigenvalue counter by 1
plot2d(total_xi,total_wf,style=color(s(n)))
gca().children(1).children(1).thickness=3;
plot([total_xi(1),total_xi($)],[E_m,E_m],'k')/* Plot horizontal
line at the eigenvalue */
end
disp(Eigen)
gca().font_size=5;
title("$Eigenvalues\ \&\ Eigenfunctions\ of\ Double\ Well\ Potential\ V=\frac{\epsilon}{\delta^2}
xlabel("$\xi = \sqrt{\frac{\epsilon m}{\delta^2\hbar}(x^2-\delta)}\rightarrow$", "fontsize",5)
ylabel("$Energy\ E\rightarrow$","fontsize",5)
y = (1/4)*(total_xi**2-4)**2
plot(total_xi,y,'-.m', 'linewidth',2)

Here δ = 2;  = 2 was taken as parameter

49
7.2.2 Output

Figure 7.3: Eigenfunctions of double well potential for l = 1 case.

Outcomes of some other codes are also given below:


Some observations are listed here. As expected, the higher eigenstates have the same form as
that of the QSHO eigenstates, i.e., they look like a polynomial times a gaussian. The lower
eigenstates, and particularly the ground state differs from the pure gaussian that the QSHO
ground state is. We can plot just the first 2 eigenstates.The red curve is the ground state and is
clearly not a gaussian. The particle in this state has high probability of being on either side of
the bulge in the well and low probability of being in the center of the potential. All of this stands
in stark contrast to the case for the QSHO ground state which shows the opposite behaviour.
The first excited state does not appear to be affected much by the bulge because even if the
bulge was not there, the QSHO first excited state already has low probability of the particle
being in the center. The higher eigenstates are not much affected by the bulge in the center as
their eigenvalues lie above the bulge height as seen in the first plot. The eigenenergies of the
potential were also calculated.

50
Figure 7.4: Eigenfunctions of double well potential for l = 1 case.

(a) Eigenfunctions of double well


potential.© Dhruv Sood (b) Zoomed in picture of the first two states.

51
Figure 7.6: Eigenfunctions of the double well potential.© Priyanshi Srivastava

52
Bibliography

[1] Jaan Kiusalaas. Numerical Methods in Engineering with Python 3. 3rd ed. Cambridge
University Press, 2013. doi: 10.1017/CBO9781139523899 (page 2).
[2] Q. Kong, T. Siauw, and A. Bayen. Python Programming and Numerical Methods:
A Guide for Engineers and Scientists. Elsevier Science, 2020. isbn: 9780128195505.
url: https://books.google.co.in/books?id=GWzqDwAAQBAJ (page 10).
[3] G. Moruzzi. Essential Python for the Physicist. Springer International Publishing,
2020. isbn: 9783030450267. url: https : / / books . google . co . in / books ? id =
mhZpzQEACAAJ (page 15).
[4] D.J. Griffiths and P.D.J. Griffiths. Introduction to Quantum Mechanics. Pearson in-
ternational edition. Pearson Prentice Hall, 2005. isbn: 9780131118928. url: https:
//books.google.co.in/books?id=z4fwAAAAMAAJ (pages 15, 29, 32).

53

View publication stats

You might also like