Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

work on limits section #134

Merged
merged 1 commit into from
Jul 2, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions quarto/_quarto.yml
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
version: "0.20"
version: "0.21"
engine: julia

project:
Expand All @@ -23,7 +23,7 @@ book:
pinned: false
sidebar:
collapse-level: 1
page-footer: "Copyright 2022, John Verzani"
page-footer: "Copyright 2022-24, John Verzani"
chapters:
- index.qmd
- part: precalc.qmd
Expand Down
14 changes: 14 additions & 0 deletions quarto/index.qmd
Original file line number Diff line number Diff line change
Expand Up @@ -68,11 +68,25 @@ and loads some useful packages that will be used repeatedly.
These notes are presented as a Quarto book. To learn more about Quarto
books visit <https://quarto.org/docs/books>.

<!--
These notes may be compiled into a `pdf` file through Quarto. As the result is rather large, we do not provide that file for download. For the interested reader, downloading the repository, instantiating the environment, and running `quarto` to render to `pdf` in the `quarto` subdirectory should produce that file (after some time).
-->

To *contribute* -- say by suggesting addition topics, correcting a
mistake, or fixing a typo -- click the "Edit this page" link and join the list of [contributors](https://github.com/jverzani/CalculusWithJuliaNotes.jl/graphs/contributors). Thanks to all contributors and a *very* special thanks to `@fangliu-tju` for their careful and most-appreciated proofreading.

## Running Julia

`Julia` is installed quite easily with the `juliaup` utility. There are some brief installation notes in the overview of `Julia` commands. To run `Julia` through the web (though in a resource-constrained manner), these links resolve to `binder.org` instances:


* [![Binder](https://mybinder.org/badge_logo.svg)](https://mybinder.org/v2/gh/jverzani/CalculusWithJuliaBinder.jl/main?labpath=blank-notebook.ipynb) (Image without SymPy)


* [![Binder](https://mybinder.org/badge_logo.svg)](https://mybinder.org/v2/gh/jverzani/CalculusWithJuliaBinder.jl/sympy?labpath=blank-notebook.ipynb) (Image with SymPy, longer to load)



----

Calculus with Julia version {{< meta version >}}, produced on {{< meta date >}}.
19 changes: 18 additions & 1 deletion quarto/integrals/area.qmd
Original file line number Diff line number Diff line change
Expand Up @@ -974,7 +974,7 @@ let
F = FnWrapper(f)
ans,err = quadgk(F, a, b)
plot(f, a, b, legend=false, title="Error ≈ $(round(err,sigdigits=2))")
scatter!(F.xs, F.ys)
scatter!(F.xs, F.ys)
end
```

Expand Down Expand Up @@ -1047,6 +1047,23 @@ solve.(Z, (1/4, 1/2, 3/4))

The middle one is clearly $0$. This distribution is symmetric about $0$, so half the area is to the right of $0$ and half to the left, so clearly when $p=0.5$, $x$ is $0$. The other two show that the area to the left of $-0.809767$ is equal to the area to the right of $0.809767$ and equal to $0.25$.

##### Example: Gauss nodes

The `QuadGK.gauss(n)` function returns a pair of $n$ quadrature points and weights to integrate a function over the interval $(-1,1)$, with an option to use a different interval $(a,b)$. For a given $n$, these values exactly integrate any polynomial of degree $2n-1$ or less. The pattern to integrate below can be expressed in other ways, but this is intended to be direct:


```{julia}
xs, ws = QuadGK.gauss(5)
```

```{julia}
f(x) = exp(cos(x))
sum(w * f(x) for (x, w) in zip(xs, ws))
```

The `zip` function is used to iterate over the `xs` and `ws` as pairs of values.



## Questions

Expand Down
17 changes: 13 additions & 4 deletions quarto/limits/continuity.qmd
Original file line number Diff line number Diff line change
Expand Up @@ -76,6 +76,8 @@ This speaks to continuity at a point, we can extend this to continuity over an i

Finally, as with limits, it can be convenient to speak of *right* continuity and *left* continuity at a point, where the limit in the definition is replaced by a right or left limit, as appropriate.

In particular, a function is *continuous* over $[a,b]$ if it is continuous on $(a,b)$, left continuous at $b$ and right continuous at $a$.


:::{.callout-warning}
## Warning
Expand All @@ -90,7 +92,7 @@ Most familiar functions are continuous everywhere.


* For example, a monomial function $f(x) = ax^n$ for non-negative, integer $n$ will be continuous. This is because the limit exists everywhere, the domain of $f$ is all $x$ and there are no jumps.
* Similarly, the basic trigonometric functions $\sin(x)$, $\cos(x)$ are continuous everywhere.
* Similarly, the building-block trigonometric functions $\sin(x)$, $\cos(x)$ are continuous everywhere.
* So are the exponential functions $f(x) = a^x, a > 0$.
* The hyperbolic sine ($(e^x - e^{-x})/2$) and cosine ($(e^x + e^{-x})/2$) are, as $e^x$ is.
* The hyperbolic tangent is, as $\cosh(x) > 0$ for all $x$.
Expand All @@ -103,7 +105,7 @@ Some familiar functions are *mostly* continuous but not everywhere.
* Similarly, $f(x) = \log(x)$ is continuous on $(0,\infty)$, but it is not defined at $x=0$, so is not right continuous at $0$.
* The tangent function $\tan(x) = \sin(x)/\cos(x)$ is continuous everywhere *except* the points $x$ with $\cos(x) = 0$ ($\pi/2 + k\pi, k$ an integer).
* The hyperbolic co-tangent is not continuous at $x=0$ – when $\sinh$ is $0$,
* The semicircle $f(x) = \sqrt{1 - x^2}$ is *continuous* on $(-1, 1)$. It is not continuous at $-1$ and $1$, though it is right continuous at $-1$ and left continuous at $1$.
* The semicircle $f(x) = \sqrt{1 - x^2}$ is *continuous* on $(-1, 1)$. It is not continuous at $-1$ and $1$, though it is right continuous at $-1$ and left continuous at $1$. (It is continuous on $[-1,1]$.)


##### Examples of discontinuity
Expand Down Expand Up @@ -210,6 +212,13 @@ solve(del, c)
This gives the value of $c$.


This is a bit fussier than need be. As the left and right pieces (say, $f_l$ and $f_r$) as both are polynomials are continuous everywhere, so would have left and right limits given through evaluation. Solving for `c` as follows is enough:

```{julia}
solve(ex1(x=>0) ~ ex2(x=>0), c)
```


## Rules for continuity


Expand Down Expand Up @@ -384,7 +393,7 @@ numericq(val)
###### Question


Suppose $f(x)$, $g(x)$, and $h(x)$ are continuous functions on $(a,b)$. If $a < c < b$, are you sure that $lim_{x \rightarrow c} f(g(x))$ is $f(g(c))$?
Suppose $f(x)$, $g(x)$, and $h(x)$ are continuous functions on $(a,b)$. If $a < c < b$, are you sure that $\lim_{x \rightarrow c} f(g(x))$ is $f(g(c))$?


```{julia}
Expand Down Expand Up @@ -453,7 +462,7 @@ yesnoq(true)
###### Question


Let $f(x)$ and $g(x)$ be continuous functions whose graph of $[0,1]$ is given by:
Let $f(x)$ and $g(x)$ be continuous functions. Their graphs over $[0,1]$ are given by:


```{julia}
Expand Down
26 changes: 22 additions & 4 deletions quarto/limits/intermediate_value_theorem.qmd
Original file line number Diff line number Diff line change
Expand Up @@ -76,7 +76,7 @@ ImageFile(imgfile, caption)
In the early years of calculus, the intermediate value theorem was intricately connected with the definition of continuity, now it is a consequence.


The basic proof starts with a set of points in $[a,b]$: $C = \{x \text{ in } [a,b] \text{ with } f(x) \leq y\}$. The set is not empty (as $a$ is in $C$) so it *must* have a largest value, call it $c$ (this requires the completeness property of the real numbers). By continuity of $f$, it can be shown that $\lim_{x \rightarrow c-} f(x) = f(c) \leq y$ and $\lim_{y \rightarrow c+}f(x) =f(c) \geq y$, which forces $f(c) = y$.
The basic proof starts with a set of points in $[a,b]$: $C = \{x \text{ in } [a,b] \text{ with } f(x) \leq y\}$. The set is not empty (as $a$ is in $C$) so it *must* have a largest value, call it $c$ (this might seem obvious, but it requires the completeness property of the real numbers). By continuity of $f$, it can be shown that $\lim_{x \rightarrow c-} f(x) = f(c) \leq y$ and $\lim_{y \rightarrow c+}f(x) =f(c) \geq y$, which forces $f(c) = y$.


### Bolzano and the bisection method
Expand All @@ -87,8 +87,19 @@ Suppose we have a continuous function $f(x)$ on $[a,b]$ with $f(a) < 0$ and $f(b

We use this fact when building a "sign chart" of a polynomial function. Between any two consecutive real zeros the polynomial can not change sign. (Why?) So a "test point" can be used to determine the sign of the function over an entire interval.

The `sign_chart` function from `CalculusWithJulia` uses this to indicate where an *assumed* continuous function changes sign:

Here, we use the Bolzano theorem to give an algorithm - the *bisection method* - to locate the value $c$ under the assumption $f$ is continuous on $[a,b]$ and changes sign between $a$ and $b$.
```{julia}
f(x) = sin(x + x^2) + x/2
sign_chart(f, -3, 3)
```


The intermediate value theorem can find the sign of the function *between* adjacent zeros, but how are the zeros identified?

Here, we use the Bolzano theorem to give an algorithm - the *bisection method* - to locate a value $c$ in $[a,b]$ with $f(c) = 0$ under the assumptions:
* $f$ is continuous on $[a,b]$
* $f$ changes sign between $a$ and $b$. (In particular, when $f(a)$ and $f(b)$ have different signs.)

::: {.callout-note}
#### Between
Expand Down Expand Up @@ -339,6 +350,13 @@ find_zero(h, (0, 2))
### Solving `f(x) = g(x)` and `f(x) = c`

The above shows a means to translate a given problem into one that can be solved with `find_zero`. Basically to solve either when a function is a non-zero constant or when a function is equal to some other function, the difference between the two sides is formed and turned into a function, called `h` above.

If using symbolic expressions, as below, then an equation (formed by `~`) can be passed to `find_zero`:

```{julia}
@syms x
solve(cos(x) ~ x, (0, 2))
```
:::

##### Example: Inverse functions
Expand Down Expand Up @@ -493,7 +511,7 @@ Note that the function is infinite at `b`:
d(b)
```

From the graph, we can see the zero is around `b`. As `d(b)` is `-Inf` we can use the bracket `(b/2,b)`
From the graph, we can see the zero is around `b`. As `d(b)` is `-Inf` we can use the bracket `(b/2, b)`


```{julia}
Expand Down Expand Up @@ -569,7 +587,7 @@ find_zero(f, I), find_zero(f, I, p=2)

The second number is the solution when `p=2`.

The above used a *keyword* argument, but a positional argument allows for broadcasting:
The above used a *keyword* argument to pass in the parameter, but using a positional argument (the last one) allows for broadcasting:

```{julia}
find_zero.(f, Ref(I), 1:5) # solutions for p=1,2,3,4,5
Expand Down
52 changes: 25 additions & 27 deletions quarto/limits/limits.qmd
Original file line number Diff line number Diff line change
Expand Up @@ -238,13 +238,13 @@ annotate!([(0,0+Δ,"A"), (x-Δ,y+Δ/4, "B"), (1+Δ/2,y/x, "C"),
annotate!([(.2*cos(θ/2), 0.2*sin(θ/2), "θ")])
imgfile = tempname() * ".png"
savefig(p, imgfile)
caption = "Triangle ``ABD` has less area than the shaded wedge, which has less area than triangle ``ACD``. Their respective areas are ``(1/2)\\sin(\\theta)``, ``(1/2)\\theta``, and ``(1/2)\\tan(\\theta)``. The inequality used to show ``\\sin(x)/x`` is bounded below by ``\\cos(x)`` and above by ``1`` comes from a division by ``(1/2) \\sin(x)`` and taking reciprocals.
caption = "Triangle ``ABD`` has less area than the shaded wedge, which has less area than triangle ``ACD``. Their respective areas are ``(1/2)\\sin(\\theta)``, ``(1/2)\\theta``, and ``(1/2)\\tan(\\theta)``. The inequality used to show ``\\sin(x)/x`` is bounded below by ``\\cos(x)`` and above by ``1`` comes from a division by ``(1/2) \\sin(x)`` and taking reciprocals.
"
plotly()
ImageFile(imgfile, caption)
```

To discuss the case of $(1+x)^{1/x}$ it proved convenient to assume $x = 1/m$ for integer values of $m$. At the time of Cauchy, log tables were available to identify the approximate value of the limit. Cauchy computed the following value from logarithm tables.
To discuss the case of $(1+x)^{1/x}$ it proved convenient to assume $x = 1/m$ for integer values of $m$. At the time of Cauchy, log tables were available to identify the approximate value of the limit. Cauchy computed the following value from logarithm tables:


```{julia}
Expand Down Expand Up @@ -337,13 +337,14 @@ Let's return to the function $f(x) = \sin(x)/x$. This function was studied by Eu

```{julia}
#| hold: true

f(x) = sin(x)/x
xs, ys = unzip(f, -pi/2, pi/2) # get points used to plot `f`
plot(xs, ys)
scatter!(xs, ys)
plot(f, -pi/2, pi/2;
seriestype=[:scatter, :line], # show points and line segments
legend=false)
```

The $y$ values of the graph seem to go to $1$ as the $x$ values get close to $0$. (That the graph looks defined at $0$ is due to the fact that the points sampled to graph do not include $0$, as shown through the `scatter!` command – which can be checked via `minimum(abs, xs)`.)
The $y$ values of the graph seem to go to $1$ as the $x$ values get close to $0$. (That the graph looks defined at $0$ is due to the fact that the points sampled to graph do not include $0$.)


We can also verify Euler's intuition through this graph:
Expand Down Expand Up @@ -432,7 +433,7 @@ The `NaN` indicates that this function is indeterminate at $c=2$. A quick plot g
```{julia}
#| hold: true
c, delta = 2, 1
plot(x -> (x^2 - 5x + 6) / (x^2 + x - 6), c - delta, c + delta)
plot(f, c - delta, c + delta)
```

The graph looks "continuous." In fact, the value $c=2$ is termed a *removable singularity* as redefining $f(x)$ to be $-0.2$ when $x=2$ results in a "continuous" function.
Expand Down Expand Up @@ -585,13 +586,11 @@ g(x) = (1 - cos(x)) / x^2
g(0)
```

What is the value of $L$, if it exists? A quick attempt numerically yields:
What is the value of $L$, if it exists? Getting closer to $0$ numerically than the default yields:


```{julia}
xs = 0 .+ hs
ys = [g(x) for x in xs]
[xs ys]
lim(g, 0; n=9)
```

Hmm, the values in `ys` appear to be going to $0.5$, but then end up at $0$. Is the limit $0$ or $1/2$? The answer is $1/2$. The last $0$ is an artifact of floating point arithmetic and the last few deviations from `0.5` due to loss of precision in subtraction. To investigate, we look more carefully at the two ratios:
Expand All @@ -606,7 +605,7 @@ y2s = [x^2 for x in xs]
Looking at the bottom of the second column reveals the error. The value of `1 - cos(1.0e-8)` is `0` and not a value around `5e-17`, as would be expected from the pattern above it. This is because the smallest floating point value less than `1.0` is more than `5e-17` units away, so `cos(1e-8)` is evaluated to be `1.0`. There just isn't enough granularity to get this close to $0$.


Not that we needed to. The answer would have been clear if we had stopped with `x=1e-6`, say.
Not that we needed to. The answer would have been clear if we had stopped with `x=1e-6` (with `n=6`) say.


In general, some functions will frustrate the numeric approach. It is best to be wary of results. At a minimum they should confirm what a quick graph shows, though even that isn't enough, as this next example shows.
Expand All @@ -633,23 +632,20 @@ A plot shows the answer appears to be straightforward:


```{julia}
#| echo: false
h(x) = x^2 + 1 + log(abs(11*x - 15))/99
plot(h, 15/11 - 1, 15/11 + 1)
```

Taking values near $15/11$ shows nothing too unusual:
Taking values near $15/11$ shows nothing perhaps too unusual:


```{julia}
#| hold: true
c = 15/11
hs = [1/10^i for i in 4:3:16]
xs = c .+ hs
[xs h.(xs)]
lim(h, c; n = 16)
```

(Though both the graph and the table hint at something a bit odd.)
(Though the graph and table do hint at something a bit odd -- the graph shows a blip, the table doesn't show values in the second column going towards a specific value.)


However the limit in this case is $-\infty$ (or DNE), as there is an aysmptote at $c=15/11$. The problem is the asymptote due to the logarithm is extremely narrow and happens between floating point values to the left and right of $15/11$.
Expand Down Expand Up @@ -726,7 +722,7 @@ For example, the limit at $0$ of $(1-\cos(x))/x^2$ is easily handled:
limit((1 - cos(x)) / x^2, x => 0)
```

The pair notation (`x => 0`) is used to indicate the variable and the value it is going to.
The pair notation (`x => 0`) is used to indicate the variable and the value it is going to. A `dir` argument is used to indicate ``x \rightarrow c+`` (the default), ``x \rightarrow c-``, and ``x \rightarrow c``.


##### Example
Expand All @@ -736,16 +732,16 @@ We look again at this function which despite having a vertical asymptote at $x=1


$$
f(x) = x^2 + 1 + \log(| 11 \cdot x - 15 |)/99.
h(x) = x^2 + 1 + \log(| 11 \cdot x - 15 |)/99.
$$

We find the limit symbolically at $c=15/11$ as follows, taking care to use the exact value `15//11` and not the *floating point* approximation returned by `15/11`:


```{julia}
#| hold: true
f(x) = x^2 + 1 + log(abs(11x - 15))/99
limit(f(x), x => 15 // 11)
h(x) = x^2 + 1 + log(abs(11x - 15))/99
limit(h(x), x => 15 // 11)
```

##### Example
Expand All @@ -764,24 +760,26 @@ We have for the first:


```{julia}
limit( (2sin(x) - sin(2x)) / (x - sin(x)), x => 0)
limit( (2sin(x) - sin(2x)) / (x - sin(x)), x => 0; dir="+-")
```

(The `dir = "+-"` indicates take both a right and left limit and ensure both exist and are equal.)

The second is similarly done, though here we define a function for variety:


```{julia}
#| hold: true
f(x) = (exp(x) - 1 - x) / x^2
limit(f(x), x => 0)
limit(f(x), x => 0; dir="+-")
```

Finally, for the third we define a new variable and proceed:


```{julia}
@syms rho::real
limit( (x^(1-rho) - 1) / (1 - rho), rho => 1)
limit( (x^(1-rho) - 1) / (1 - rho), rho => 1; dir="+-")
```

This last limit demonstrates that the `limit` function of `SymPy` can readily evaluate limits that involve parameters, though at times some assumptions on the parameters may be needed, as was done through `rho::real`.
Expand Down Expand Up @@ -842,7 +840,7 @@ limit(f(x), x => PI/2)
Right and left limits will be discussed in the next section; here we give an example of the idea. The mathematical convention is to say a limit exists if both the left *and* right limits exist and are equal. Informally a right (left) limit at $c$ only considers values of $x$ more (less) than $c$. The `limit` function of `SymPy` finds directional limits by default, a right limit, where $x > c$.


The left limit can be found by passing the argument `dir="-"`. Passing `dir="+-"` (and not `"-+"`) will compute the mathematical limit, throwing an error in `Python` if no limit exists.
The left limit can be found by passing the argument `dir="-"`. Passing `dir="+-"` (and not `"-+"`), as done in a few examples above, will compute the mathematical limit, throwing an error in `Python` if no limit exists.


```{julia}
Expand Down Expand Up @@ -938,7 +936,7 @@ as this is the limit of $f(g(x))$ with $f$ as above and $g(x) = x^2$. We need $
##### Example: products


Consider this complicated limit found on this [Wikipedia](http://en.wikipedia.org/wiki/L%27H%C3%B4pital%27s_rule) page.
Consider this more complicated limit found on this [Wikipedia](http://en.wikipedia.org/wiki/L%27H%C3%B4pital%27s_rule) page.


$$
Expand Down
Loading