Skip to content

Commit 6ff27cb

Browse files
committed
Fixed typos (incl code), wording.
1 parent 2559bf8 commit 6ff27cb

File tree

1 file changed

+23
-23
lines changed

1 file changed

+23
-23
lines changed

04-code-vectorization.rst

Lines changed: 23 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -63,7 +63,7 @@ outputs:
6363
6464
The first method concatenates the two lists together, the second method
6565
concatenates the internal lists together and the last one computes what is
66-
(numerically) expected. As an exercise, you can rewrite the python version
66+
(numerically) expected. As an exercise, you can rewrite the Python version
6767
such that it accepts nested lists of any depth.
6868

6969

@@ -74,7 +74,7 @@ Uniform vectorization is the simplest form of vectorization where all the
7474
elements share the same computation at every time step with no specific
7575
processing for any element. One stereotypical case is the Game of Life that has
7676
been invented by John Conway (see below) and is one of the earliest examples of
77-
cellular automata. Those cellular automata can be conveniently considered as
77+
cellular automata. Those cellular automata can be conveniently regarded as
7878
an array of cells that are connected together with the notion of neighbours and
7979
their vectorization is straightforward. Let me first define the game and we'll
8080
see how to vectorize it.
@@ -112,7 +112,7 @@ are directly horizontally, vertically, or diagonally adjacent. At each step in
112112
time, the following transitions occur:
113113

114114
1. Any live cell with fewer than two live neighbours dies, as if by needs
115-
caused by under population.
115+
caused by underpopulation.
116116
2. Any live cell with more than three live neighbours dies, as if by
117117
overcrowding.
118118
3. Any live cell with two or three live neighbours lives, unchanged, to the
@@ -151,7 +151,7 @@ tests for borders when counting the number of neighbours.
151151
[0,0,0,0,0,0],
152152
[0,0,0,0,0,0]]
153153
154-
Taking the border into account, counting neighbours is then straightforward:
154+
Taking the border into account, counting neighbours then is straightforward:
155155

156156
.. code:: python
157157
@@ -166,7 +166,7 @@ Taking the border into account, counting neighbours is then straightforward:
166166
return N
167167
168168
To iterate one step in time, we then simply count the number of neighbours for
169-
each internal cell and we update the whole board according to the 4
169+
each internal cell and we update the whole board according to the four
170170
aforementioned rules:
171171

172172
.. code:: python
@@ -181,7 +181,7 @@ aforementioned rules:
181181
Z[x][y] = 1
182182
return Z
183183
184-
The figure below shows 4 iterations on a 4x4 area where the initial state is a
184+
The figure below shows four iterations on a 4x4 area where the initial state is a
185185
`glider <https://en.wikipedia.org/wiki/Glider_(Conway%27s_Life)>`_, a structure
186186
discovered by Richard K. Guy in 1970.
187187

@@ -230,7 +230,7 @@ sure to consider all the eight neighbours.
230230
Z[1:-1, :-2] + Z[1:-1,2:] +
231231
Z[2: , :-2] + Z[2: ,1:-1] + Z[2: ,2:])
232232
233-
For the rule enforcement, we can write a first version using the
233+
For the rule enforcement, we can write a first version using numpy's
234234
`argwhere
235235
<http://docs.scipy.org/doc/numpy/reference/generated/numpy.argwhere.html>`_
236236
method that will give us the indices where a given condition is True.
@@ -257,7 +257,7 @@ method that will give us the indices where a given condition is True.
257257
Z[0,:] = Z[-1,:] = Z[:,0] = Z[:,-1] = 0
258258
259259
Even if this first version does not use nested loops, it is far from optimal
260-
because of the use of the 4 `argwhere` calls that may be quite slow. We can
260+
because of the use of the four `argwhere` calls that may be quite slow. We can
261261
instead factorize the rules into cells that will survive (stay at 1) and cells
262262
that will give birth. For doing this, we can take advantage of Numpy boolean
263263
capability and write quite naturally:
@@ -350,7 +350,7 @@ Worms 2 0.16 0.08 0.054 0.063
350350
Zebrafish 0.16 0.08 0.035 0.060
351351
============= ===== ===== ===== =====
352352

353-
The figure below show some animation of the model for a specific set of parameters.
353+
The figure below shows some animations of the model for a specific set of parameters.
354354

355355

356356
.. admonition:: **Figure 4.4**
@@ -478,9 +478,9 @@ Here is the benchmark:
478478
>>> xmin, xmax, xn = -2.25, +0.75, int(3000/3)
479479
>>> ymin, ymax, yn = -1.25, +1.25, int(2500/3)
480480
>>> maxiter = 200
481-
>>> timeit("mandelbrot_1(xmin, xmax, ymin, ymax, xn, yn, maxiter)", globals())
481+
>>> timeit("mandelbrot_python(xmin, xmax, ymin, ymax, xn, yn, maxiter)", globals())
482482
1 loops, best of 3: 6.1 sec per loop
483-
>>> timeit("mandelbrot_2(xmin, xmax, ymin, ymax, xn, yn, maxiter)", globals())
483+
>>> timeit("mandelbrot_numpy(xmin, xmax, ymin, ymax, xn, yn, maxiter)", globals())
484484
1 loops, best of 3: 1.15 sec per loop
485485
486486
@@ -492,10 +492,10 @@ expected. Part of the problem is that the `np.less` function implies
492492
:math:`xn \times yn` tests at every iteration while we know that some
493493
values have already diverged. Even if these tests are performed at the
494494
C level (through numpy), the cost is nonetheless
495-
non-negligible. Another approach proposed by `Dan Goodman
495+
significant. Another approach proposed by `Dan Goodman
496496
<https://thesamovar.wordpress.com/>`_ is to work on a dynamic array at
497497
each iteration that stores only the points which have not yet
498-
diverged. It requires more lines but the result is faster and lead to
498+
diverged. It requires more lines but the result is faster and leads to
499499
a 10x factor speed improvement compared to the Python version.
500500

501501
.. code-block:: python
@@ -534,7 +534,7 @@ The benchmark gives us:
534534

535535
.. code-block:: pycon
536536
537-
>>> timeit("mandelbrot_3(xmin, xmax, ymin, ymax, xn, yn, maxiter)", globals())
537+
>>> timeit("mandelbrot_numpy_2(xmin, xmax, ymin, ymax, xn, yn, maxiter)", globals())
538538
1 loops, best of 3: 510 msec per loop
539539
540540
Visualization
@@ -611,11 +611,11 @@ Spatial vectorization
611611

612612
Spatial vectorization refers to a situation where elements share the same
613613
computation but are in interaction with only a subgroup of other elements. This
614-
was already the case for the game of life example, but in the present case
614+
was already the case for the game of life example, but in some situations
615615
there is an added difficulty because the subgroup is dynamic and needs to be
616616
updated at each iteration. This the case, for example, in particle systems where
617617
particles interact mostly with local neighbours. This is also the case for
618-
boids that simulate flocking behaviors.
618+
"boids" that simulate flocking behaviors.
619619

620620
.. admonition:: **Figure 4.8**
621621
:class: legend
@@ -680,7 +680,7 @@ position and velocity, it seems natural to start by writing a Boid class:
680680
681681
The `vec2` object is a very simple class that handles all common vector
682682
operations with 2 components. It will save us some writing in the main `Boid`
683-
class. Note that there are some vector packages in the python package index, but
683+
class. Note that there are some vector packages in the Python Package Index, but
684684
that would be overkill for such a simple example.
685685

686686
Boid is a difficult case for regular Python because a boid has interaction with
@@ -724,7 +724,7 @@ To complete the picture, we can also create a `Flock` object:
724724
725725
Using this approach, we can have up to 50 boids until the computation
726726
time becomes too slow for a smooth animation. As you may have guessed,
727-
we can do much better using numpy but let me first point out the main
727+
we can do much better using numpy, but let me first point out the main
728728
problem with this Python implementation. If you look at the code, you
729729
will certainly notice there is a lot of redundancy. More precisely, we
730730
do not exploit the fact that the Euclidean distance is reflexive, that
@@ -748,8 +748,8 @@ we'll gather all our boids into a `position` array and a `velocity` array:
748748
velocity = np.zeros((n, 2), dtype=np.float32)
749749
position = np.zeros((n, 2), dtype=np.float32)
750750
751-
The first step is to compute the local neighborhood for each boids and for
752-
this, we need to compute all paired distances:
751+
The first step is to compute the local neighborhood for all boids, and for
752+
this we need to compute all paired distances:
753753

754754
.. code:: python
755755
@@ -760,7 +760,7 @@ this, we need to compute all paired distances:
760760
We could have used the scipy `cdist
761761
<https://docs.scipy.org/doc/scipy/reference/generated/scipy.spatial.distance.cdist.html>`_
762762
but we'll need the `dx` and `dy` arrays later. Once those have been computed,
763-
it's faster to use the `hypot
763+
it is faster to use the `hypot
764764
<https://docs.scipy.org/doc/numpy/reference/generated/numpy.hypot.html>`_
765765
method. Note that distance shape is `(n, n)` and each line relates to one boid,
766766
i.e. each line gives the distance to all other boids (including self).
@@ -947,13 +947,13 @@ We've seen through these examples three forms of code vectorization:
947947
* uniform vectorization where elements share the same computation
948948
unconditionally and for the same duration.
949949
* temporal vectorization where elements share the same computation but
950-
necessitate a different number of iteration
950+
necessitate a different number of iterations
951951
* spatial vectorization where elements share the same computation but on
952952
dynamic spatial arguments
953953

954954
And there are probably many more forms of such direct code vectorization. As
955955
explained before, this kind of vectorization is one of the most simple even
956-
though we've seen it can be real tricky to implement and require some
956+
though we've seen it can be really tricky to implement and requires some
957957
experience, some help or both. For example, the solution to the boids exercise
958958
was provided by `Divakar <http://stackoverflow.com/users/3293881/divakar>`_ on
959959
`stack overflow <http://stackoverflow.com/questions/40822983/multiple-individual-2d-rotation-at-once>`_ after having explained my problem.

0 commit comments

Comments
 (0)