diff --git a/source/rst/functions.md b/source/rst/functions.md index 346cb1b3..3d10e9d6 100644 --- a/source/rst/functions.md +++ b/source/rst/functions.md @@ -88,7 +88,7 @@ If the built-in functions don't cover what we need, we either need to import functions or create our own. Examples of importing and using functions -were given in the previous lecture +were given in the {doc}`previous lecture ` Here's another one, which tests whether a given year is a leap year: @@ -168,13 +168,13 @@ User-defined functions are important for improving the clarity of your code by (Writing the same thing twice is [almost always a bad idea](https://en.wikipedia.org/wiki/Don%27t_repeat_yourself)) -We will say more about this later. +We will say more about this {doc}`later `. ## Applications ### Random Draws -Consider again this code from the previous lecture +Consider again this code from the {doc}`previous lecture ` ```{code-block} python3 ts_length = 100 diff --git a/source/rst/need_for_speed.md b/source/rst/need_for_speed.md index 953bb0a1..6d68c6b1 100644 --- a/source/rst/need_for_speed.md +++ b/source/rst/need_for_speed.md @@ -459,5 +459,5 @@ with vectorization listed above. It does so through something called **just in time (JIT) compilation**, which can generate extremely fast and efficient code. -We'll learn how to use Numba soon. +We'll learn how to use Numba {doc}`soon `. diff --git a/source/rst/numba.md b/source/rst/numba.md index a5dd6b2a..d5b3cdbc 100644 --- a/source/rst/numba.md +++ b/source/rst/numba.md @@ -19,7 +19,7 @@ In addition to what's in Anaconda, this lecture will need the following librarie ``` Please also make sure that you have the latest version of Anaconda, since old -versions are a common source of errors. +versions are a {doc}`common source of errors `. Let's start with some imports: @@ -33,12 +33,12 @@ import matplotlib.pyplot as plt ## Overview -In an earlier lecture we learned about vectorization, which is one method to improve speed and efficiency in numerical work. +In an {doc}`earlier lecture ` we learned about vectorization, which is one method to improve speed and efficiency in numerical work. Vectorization involves sending array processing operations in batch to efficient low-level code. -However, as discussed previously, vectorization has several weaknesses. +However, as {ref}`discussed previously `, vectorization has several weaknesses. One is that it is highly memory-intensive when working with large amounts of data. @@ -157,7 +157,7 @@ Numba attempts to generate fast machine code using the infrastructure provided b It does this by inferring type information on the fly. -(See our earlier lecture on scientific computing for a discussion of types.) +(See our {doc}`earlier lecture ` on scientific computing for a discussion of types.) The basic idea is this: @@ -187,7 +187,7 @@ qm_numba = jit(qm) In practice this would typically be done using an alternative *decorator* syntax. -(We will explain all about decorators in a later lecture but you can skip the details at this stage.) +(We will explain all about decorators in a {doc}`later lecture ` but you can skip the details at this stage.) Let's see how this is done. @@ -264,7 +264,7 @@ If a class is successfully compiled, then its methods act as JIT-compiled functions. To give one example, let's consider the class for analyzing the Solow growth model we -created in this lecture. +created in {doc}`this lecture `. To compile this class we use the `@jitclass` decorator: @@ -379,7 +379,7 @@ If you prefer, you can safely skip this section. ### Cython -Like Numba, [Cython](http://cython.org/) provides an approach to generating fast compiled code that can be used from Python. +Like {doc}`Numba `, [Cython](http://cython.org/) provides an approach to generating fast compiled code that can be used from Python. As was the case with Numba, a key problem is the fact that Python is dynamically typed. @@ -461,7 +461,7 @@ When Numba compiles machine code for functions, it treats global variables as co ### Exercise 1 -Previously we considered how to approximate $\pi$ by +{ref}`Previously ` we considered how to approximate $\pi$ by Monte Carlo. Use the same idea here, but make the code efficient using Numba. diff --git a/source/rst/numpy.md b/source/rst/numpy.md index 16dca6e9..7de48aa0 100644 --- a/source/rst/numpy.md +++ b/source/rst/numpy.md @@ -503,7 +503,7 @@ a What's happened is that we have changed `a` by changing `b`. The name `b` is bound to `a` and becomes just another reference to the -array (the Python assignment model is described in more detail later in the course). +array (the Python assignment model is described in more detail {doc}`later in the course `). Hence, it has equal rights to make changes to that array. @@ -700,7 +700,7 @@ single: Python; SciPy Much of this functionality is also available in [SciPy](http://www.scipy.org/), a collection of modules that are built on top of NumPy. -We'll cover the SciPy versions in more detail soon. +We'll cover the SciPy versions in more detail {doc}`soon `. For a comprehensive list of what's available in NumPy see [this documentation](https://docs.scipy.org/doc/numpy/reference/routines.html). @@ -716,7 +716,7 @@ Consider the polynomial expression p(x) = a_0 + a_1 x + a_2 x^2 + \cdots a_N x^N = \sum_{n=0}^N a_n x^n ``` -Earlier, you wrote a simple function `p(x, coeff)` to evaluate `np_polynom` without considering efficiency. +{ref}`Earlier `, you wrote a simple function `p(x, coeff)` to evaluate {eq}`np_polynom ` without considering efficiency. Now write a new function that does the same job, but uses NumPy arrays and array operations for its computations, rather than any form of Python loop. @@ -771,7 +771,7 @@ If you can, write the method so that `draw(k)` returns `k` draws from `q`. ### Exercise 3 -Recall our earlier discussion of the empirical cumulative distribution function. +Recall our {ref}`earlier discussion ` of the empirical cumulative distribution function. Your task is to diff --git a/source/rst/pandas.md b/source/rst/pandas.md index c24d87bc..641cbee6 100644 --- a/source/rst/pandas.md +++ b/source/rst/pandas.md @@ -462,7 +462,7 @@ Complete the program to plot the result as a bar graph like this one: ### Exercise 2 -Using the method `read_data` introduced in Exercise 1, write a program to obtain year-on-year percentage change for the following indices: +Using the method `read_data` introduced in {ref}`Exercise 1 `, write a program to obtain year-on-year percentage change for the following indices: ```{code-block} python3 indices_list = {'^GSPC': 'S&P 500', @@ -516,7 +516,7 @@ plt.show() ### Exercise 2 -Following the work you did in Exercise 1, you can query the data using `read_data` by updating the start and end dates accordingly. +Following the work you did in {ref}`Exercise 1 `, you can query the data using `read_data` by updating the start and end dates accordingly. ```{code-block} python3 indices_data = read_data( diff --git a/source/rst/parallelization.md b/source/rst/parallelization.md index 2dcc7a23..5ec051a3 100644 --- a/source/rst/parallelization.md +++ b/source/rst/parallelization.md @@ -146,7 +146,7 @@ distributes them to different threads. Over the last few years, NumPy has managed to push this kind of multithreading out to more and more operations. -For example, let's return to a maximization problem discussed previously: +For example, let's return to a maximization problem {ref}`discussed previously `: ```{code-block} python3 def f(x, y): @@ -176,7 +176,7 @@ To get some basis for comparison for the last example, let's try the same thing with Numba. In fact there is an easy way to do this, since Numba can also be used to -create custom ufuncs with the [@vectorize](http://numba.pydata.org/numba-doc/dev/user/vectorize.html) decorator. +create custom {ref}`ufuncs ` with the [@vectorize](http://numba.pydata.org/numba-doc/dev/user/vectorize.html) decorator. ```{code-block} python3 from numba import vectorize @@ -406,7 +406,7 @@ When you see us using ordinary `range` in a jitted function, it is either becaus ### Exercise 1 -In an earlier exercise, we used Numba to accelerate an +In {ref}`an earlier exercise `, we used Numba to accelerate an effort to compute the constant $\pi$ by Monte Carlo. Now try adding parallelization and see if you get further speed gains. diff --git a/source/rst/python_advanced_features.md b/source/rst/python_advanced_features.md index 683284fe..183605ea 100644 --- a/source/rst/python_advanced_features.md +++ b/source/rst/python_advanced_features.md @@ -29,7 +29,7 @@ A variety of topics are treated in the lecture, including generators, exceptions single: Python; Iteration ``` -We've already said something about iterating in Python. +We've {ref}`already said something ` about iterating in Python. Now let's look more closely at how it all works, focusing in Python's implementation of the `for` loop. @@ -47,7 +47,7 @@ Formally, an *iterator* is an object with a `__next__` method. For example, file objects are iterators . -To see this, let's have another look at the US cities data, +To see this, let's have another look at the {ref}`US cities data `, which is written to the present working directory in the following cell ```{code-block} ipython diff --git a/source/rst/python_by_example.md b/source/rst/python_by_example.md index 5a7d7489..d4297016 100644 --- a/source/rst/python_by_example.md +++ b/source/rst/python_by_example.md @@ -26,7 +26,7 @@ The objective is to introduce you to basic Python syntax and data structures. Deeper concepts will be covered in later lectures. -You should have read the lecture on getting started with Python before beginning this one. +You should have read the {doc}`lecture ` on getting started with Python before beginning this one. ## The Task: Plotting a White Noise Process @@ -72,7 +72,7 @@ Let's break this program down and see how it works. The first two lines of the program import functionality from external code libraries. -The first line imports NumPy, a favorite Python package for tasks like +The first line imports {doc}`NumPy `, a favorite Python package for tasks like * working with arrays (vectors and matrices) * common mathematical functions like `cos` and `sqrt` @@ -194,7 +194,7 @@ We can and will look at various ways to configure and improve this plot below. ## Alternative Implementations -Let's try writing some alternative versions of our first program, which plotted IID draws from the normal distribution. +Let's try writing some alternative versions of {ref}`our first program `, which plotted IID draws from the normal distribution. The programs below are less efficient than the original one, and hence somewhat artificial. @@ -294,7 +294,7 @@ x[1] # second element of x single: Python; For loop ``` -Now let's consider the `for` loop from the program above, which was +Now let's consider the `for` loop from {ref}`the program above `, which was ```{code-block} python3 for i in range(ts_length): @@ -368,7 +368,7 @@ single: Python; While loop The `for` loop is the most common technique for iteration in Python. -But, for the purpose of illustration, let's modify the program above to use a `while` loop instead. +But, for the purpose of illustration, let's modify {ref}`the program above ` to use a `while` loop instead. ```{code-block} python3 ts_length = 100 diff --git a/source/rst/python_essentials.md b/source/rst/python_essentials.md index 3f16ecdf..b66e3476 100644 --- a/source/rst/python_essentials.md +++ b/source/rst/python_essentials.md @@ -112,7 +112,7 @@ type(x) Python has several basic types for storing collections of (possibly heterogeneous) data. -We've already discussed lists. +We've {ref}`already discussed lists `. ```{index} single: Python; Tuples @@ -163,7 +163,7 @@ x y ``` -You've actually seen an example of this already. +You've actually {ref}`seen an example of this ` already. Tuple unpacking is convenient and we'll use it often. @@ -564,7 +564,7 @@ Let's talk a bit more about functions, which are all important for good programm ### The Flexibility of Python Functions -As we discussed in the previous lecture, Python functions are very flexible. +As we discussed in the {ref}`previous lecture `, Python functions are very flexible. In particular @@ -573,7 +573,7 @@ In particular * Any object can be passed to a function as an argument, including other functions. * A function can return any kind of object, including functions. -We already gave an example of how straightforward it is to pass a function to +We already {ref}`gave an example ` of how straightforward it is to pass a function to a function. Note that a function can have arbitrarily many `return` statements (including zero). @@ -688,7 +688,7 @@ Here the function created by `lambda` is said to be *anonymous* because it was n single: Python; keyword arguments ``` -In a previous lecture, you came across the statement +In a {ref}`previous lecture `, you came across the statement ```{code-block} python3 plt.plot(x, 'b-', label="white noise") @@ -778,7 +778,7 @@ p(x) = \sum_{i=0}^n a_i x^i ``` -Write a function `p` such that `p(x, coeff)` that computes the value in `polynom0` given a point `x` and a list of coefficients `coeff`. +Write a function `p` such that `p(x, coeff)` that computes the value in {eq}`polynom0 ` given a point `x` and a list of coefficients `coeff`. Try to use `enumerate()` in your loop. diff --git a/source/rst/python_oop.md b/source/rst/python_oop.md index ba60c26b..c54c4bdb 100644 --- a/source/rst/python_oop.md +++ b/source/rst/python_oop.md @@ -18,7 +18,7 @@ single: Python; Object-Oriented Programming ## Overview -In an earlier lecture, we learned some foundations of object-oriented programming. +In an {doc}`earlier lecture `, we learned some foundations of object-oriented programming. The objectives of this lecture are @@ -72,7 +72,7 @@ Let's cover general OOP concepts before we specialize to Python. single: Object-Oriented Programming; Key Concepts ``` -As discussed an earlier lecture, in the OOP paradigm, data and functions are **bundled together** into "objects". +As discussed an {doc}`earlier lecture `, in the OOP paradigm, data and functions are **bundled together** into "objects". An example is a Python list, which not only stores data but also knows how to sort itself, etc. @@ -302,7 +302,7 @@ There are no examples of the last rule in the preceding code but we will see som In this section, we look at some more formal details related to classes and `self` -* You might wish to skip to the next section the first time you read this lecture. +{ref}`the next section `* You might wish to skip to the first time you read this lecture. * You can return to these details after you've familiarized yourself with more examples. Methods actually live inside a class object formed when the interpreter reads @@ -368,15 +368,15 @@ Here * $n$ is the population growth rate * $\delta$ is the depreciation rate -A **steady state** of the model is a $k$ that solves `solow_lom` when $k_{t+1} = k_t = k$. +A **steady state** of the model is a $k$ that solves {eq}`solow_lom ` when $k_{t+1} = k_t = k$. Here's a class that implements this model. Some points of interest in the code are -* An instance maintains a record of its current capital stock in the variable `self.k`. -* The `h` method implements the right-hand side of `solow_lom`. -* The `update` method uses `h` to update capital as per `solow_lom`. +{eq}`solow_lom `{eq}`solow_lom `* An instance maintains a record of its current capital stock in the variable `self.k`. +* The `h` method implements the right-hand side of . +* The `update` method uses `h` to update capital as per . * Notice how inside `update` the reference to the local method `h` is `self.h`. The methods `steady_state` and `generate_sequence` are fairly self-explanatory @@ -666,7 +666,7 @@ ax.set_ylabel('$x_t$', fontsize=16) plt.show() ``` -On the horizontal axis is the parameter $r$ in `quadmap2`. +On the horizontal axis is the parameter $r$ in {eq}`quadmap2 `. The vertical axis is the state space $[0, 1]$. @@ -780,7 +780,7 @@ Aim for clarity, not efficiency. ### Exercise 2 -In an earlier exercise, you wrote a function for evaluating polynomials. +In an {ref}`earlier exercise `, you wrote a function for evaluating polynomials. This exercise is an extension, where the task is to build a simple class called `Polynomial` for representing and manipulating polynomial functions such as @@ -791,11 +791,11 @@ p(x) = a_0 + a_1 x + a_2 x^2 + \cdots a_N x^N = \sum_{n=0}^N a_n x^n \qquad (x \in \mathbb{R}) ``` -The instance data for the class `Polynomial` will be the coefficients (in the case of `polynom`, the numbers $a_0, \ldots, a_N$). +The instance data for the class `Polynomial` will be the coefficients (in the case of {eq}`polynom `, the numbers $a_0, \ldots, a_N$). Provide methods that -1. Evaluate the polynomial `polynom`, returning $p(x)$ for any $x$. +{eq}`polynom `1. Evaluate the polynomial , returning $p(x)$ for any $x$. 1. Differentiate the polynomial, replacing the original coefficients with those of its derivative $p'$. Avoid using any `import` statements. diff --git a/source/rst/scipy.md b/source/rst/scipy.md index 1d5a9536..8fa3f951 100644 --- a/source/rst/scipy.md +++ b/source/rst/scipy.md @@ -245,7 +245,7 @@ def bisect(f, a, b, tol=10e-5): return 0.5 * (upper + lower) ``` -Let's test it using the function $f$ defined in `root_f` +Let's test it using the function $f$ defined in {eq}`root_f ` ```{code-block} python3 bisect(f, 0, 1) @@ -253,7 +253,7 @@ bisect(f, 0, 1) Not surprisingly, SciPy provides its own bisection function. -Let's test it using the same function $f$ defined in `root_f` +Let's test it using the same function $f$ defined in {eq}`root_f ` ```{code-block} python3 from scipy.optimize import bisect @@ -437,11 +437,11 @@ We leave you to investigate the [set of available routines](http://docs.scipy.or ### Exercise 1 -Previously we discussed the concept of recursive function calls. +Previously we discussed the concept of {ref}`recursive function calls `. -Try to write a recursive implementation of homemade bisection function described above. +Try to write a recursive implementation of homemade bisection function {ref}`described above `. -Test it on the function `root_f`. +Test it on the function {eq}`root_f `. ## Solutions diff --git a/source/rst/troubleshooting.md b/source/rst/troubleshooting.md index 16c40782..a7bc760a 100644 --- a/source/rst/troubleshooting.md +++ b/source/rst/troubleshooting.md @@ -21,7 +21,7 @@ The basic assumption of the lectures is that code in a lecture should execute wh 1. it is executed in a Jupyter notebook and 1. the notebook is running on a machine with the latest version of Anaconda Python. -You have installed Anaconda, haven't you, following the instructions in this lecture? +You have installed Anaconda, haven't you, following the instructions in {doc}`this lecture `? Assuming that you have, the most common source of problems for our readers is that their Anaconda distribution is not up to date. diff --git a/source/rst/writing_good_code.md b/source/rst/writing_good_code.md index 8b12f420..0e0cbc4c 100644 --- a/source/rst/writing_good_code.md +++ b/source/rst/writing_good_code.md @@ -50,8 +50,8 @@ Here For each parameterization, the code -1. sets $k_0 = 1$ -1. iterates using `gc_solmod` to produce a sequence $k_0, k_1, k_2 \ldots , k_T$ +{eq}`gc_solmod `1. sets $k_0 = 1$ +1. iterates using to produce a sequence $k_0, k_1, k_2 \ldots , k_T$ 1. plots the sequence The plots will be grouped into three subfigures. @@ -205,7 +205,7 @@ While the odd global in small scripts is no big deal, we recommend that you teac For scientific computing, there is another good reason to avoid global variables. -As we've seen in previous lectures, JIT compilation can generate excellent performance for scripting languages like Python. +As {doc}`we've seen in previous lectures `, JIT compilation can generate excellent performance for scripting languages like Python. But the task of the compiler used for JIT compilation becomes harder when global variables are present.