Sei sulla pagina 1di 17

Computational Lab in Physics:

Iteration and recurrence,

Steven Kornreich
www.beachlook.com

Picture above shows a section of a Julia set, a fractal. The


study of fractals has greatly benefited from computing power.
A recurrence model: Population
growth.
 The logistic equation:
 dx/dt = r*x*(1-x)
 x represents population
fraction.
 i.e. x is between 0 and 1.
 Model:
 Growth is proportional to
available population. ~x
 Growth is inhibited by
competition for resources.
~(1-x)

2
Iteration procedure:
 xi+1 = r*xi*(1-xi)

 Population at step i+1 depends on


population at step i.
 If xi=0 (everyone’s dead), no future generations
are possible.
 If xi=1 (planet is completely crowded), the next
generation will be killed because there are not
enough resources.

 For stability, i.e. such that x is always


between 0-1, we require 0<r<4.
3
Take r=1, what happens to the
population after many iterations?

 Start with an initial population x0.


 Find x1=x0*(1-x0)
 Find x2=x1*(1-x1)
 Find x3….
 Let’s write a program for this.

4
Writing a program to do this:
 Start with x0=0.2;
 Do 10 iterations.

double recurrenceRelation(x) {
return x*(1-x);
}

int main () {
const int Niterations=10;
double values[Niterations+1];
values[0] = 0.2;
for (int i=0;i<Niterations;++i) {
values[i+1]=recurrenceRelation(values[i]);
cout << values[i+1] << endl;
}
}

5
Using the C++ standard library:
“vectors”
 Documentation:
 http://www.cplusplus.com/reference/stl/vector/
double recurrenceRelation(x) {
return x*(1-x);
}

int main () {
vector<double> values;
values.push_back(0.2);
cout << “How many iterations? “ << endl;
int Niterations;
cin << Niterations;
//push_back: puts value at the end of vector
for (int i=0;i<Niterations;++i) {
values.push_back(recurrenceRelation(values[i]));
cout << values.back() << endl;
//”back” returns the value at the end of the vector.
}
}

6
Output of 10 iterations
0.16
0.1344
0.116337
0.102802
0.0922341
0.083727
0.0767168
0.0708313
0.0658142
0.0614827
 What if I want more iterations?

7
After more iterations…

After 50 iterations…
After 200 iterations…
0.0220701
0.0050558
0.021583
0.00503024
0.0211172
0.00500494
0.0206713
0.00497989
0.020244
0.00495509
0.0198341
0.00493054
0.0194407
0.0190628
0.00490623  Check this: r<1,
0.00488216
0.0186994 for N →∞
0.00485832
0.0183497  Write a program
0.00483472
0.018013
0.0176886
0.00481134  xN → 0 for N →∞
0.00478819
0.0173757
8
What happens for r>1?
 The population dies out if r is 1 (or less).

 What if r=2?
 For 10 iterations
0.32
0.4352
0.491602
0.499859
0.5
0.5
0.5
0.5
0.5
0.5
 What if r=1.5, or r=2.5?
 At this point, we can modify the program to make it easy to switch to a
different value of r.

9
Example program: recurrence3
#include <iostream>
using std::cout;
using std::endl;
using std::cin;
double recurrenceRelation(double x,double r) {
return r*x*(1-x);
}
int main () {
const int Niterations=10;
cout << "Enter value of r" << endl;
double rInput;
cin >> rInput;
double values[Niterations+1];
values[0] = 0.2;

for (int i=0;i<Niterations;++i) {


values[i+1]=recurrenceRelation(values[i],rInput);
cout << values[i+1] << endl;
}
}
10
What happens as we increase r?
 For 1.1, 1.5, 2.0, 2.5 …
 Maybe need to increase iterations?
 the recurrence relation converges to a
fixed point.

 Does this behavior continue? What


happens for r=3?

11
Bifurcation…
 After 2000 iterations…
0.661359
0.67189
0.661361
0.671888
0.661364
0.671885
0.661367
0.671883
0.661369
0.67188
 What happens as we increase r more? r=3.2?
0.513045
0.799455

12
What if we wanted to study r
dependence?
 Need to calculate many iterations for each r.
 We have seen:
 For r<1, the recurrence relation seems to converge to
0.
 For r>1, after many iterations, the recurrence
relation seems to converge to a fixed number.
 There are cases where we get a pair of numbers.
 For a given value of r, need to store multiple
values (i.e. the xi).
 Can use ROOT histograms for this purpose.

13
Brief interlude: using 2-D Histograms.
 void histogramExample() {

//Create the histogram.


TH2D* histo2d = new TH2D("histo2d","Histogram 2D",100,-4,4,100,-4,4);

// Fill the histogram with some numbers.


// As an example, use a gaussian distribution, which
// can be obtained from the TRandom class, using the Gaus method.
//
TRandom rnd(0); // argument is the initial seed of the generator.
for (int i=0; i<30000; ++i) {
double x = rnd.Gaus(0,1); // arguments are mean, sigma. Defaults are (0,1).
double y = rnd.Gaus(0,1);
histo2d->Fill(x,y);
}

// Make a canvas and draw the histogram


// using a nice palette
TCanvas* cnv = new TCanvas("cnv","A 2D Histogram",500,500);
gStyle->SetPalette(1,0);
histo2d->Draw("col");

return;
}
14
Output of Example
 Other Draw
options:
 surf, surf2,
surf3
 col, colz

 box

 lego, lego2

 conto

15
Homework program:
 We are getting interesting behavior as we vary r. Let’s
vary r systematically.
 Explore the behavior of the “logistic map”
 xi+1 = rxi*(1-xi) for 1<r<4
 Make a root macro to plot the behaviour:
 use a 2-D histogram
 x-axis is the value of r.
 y-axis are the values calculated by recursion relation.
 Sample r from 1 to 4 in 1000 steps
 Histogram will have 1000 bins in x axis.
 Use 2000 bins in the y axis.
 Calculate 1000 iterations of the recursion for each value of r.
 Fill results into histogram after 100 iterations are done.
 Plot 2-D histogram.
 ROOT Histograms:
 ftp://root.cern.ch/root/doc/3Histograms.pdf

16
From 1 to
3.2…

 For range 0-1,


converges to 0.
 For range 1 to ~3,
convergence.
 From ~3 to 3.2 the
iteration oscillates
between 2 values.

 What happens in
the range 3.2 - 4?
17

Potrebbero piacerti anche