Real-time collaboration for Jupyter Notebooks, Linux Terminals, LaTeX, VS Code, R IDE, and more,
all in one place. Commercial Alternative to JupyterHub.
Real-time collaboration for Jupyter Notebooks, Linux Terminals, LaTeX, VS Code, R IDE, and more,
all in one place. Commercial Alternative to JupyterHub.
Lecture 3 : Numbers and symbolic expressions
References:
Summary:
In todays lecture, we'll start with a reminder of conditional execution (if
) and loop (for
) in Python, and the datatype of dictionaries. Then we discuss various types of numbers in SageMath, such as integers, rationals, algebraic numbers and more. In the last part, we discuss symbolic expressions and how to use them to solve equations.
Python warmup : conditional execution (if/else)
Sometimes we want to perform some operations in our code (like computing the inverse of a matrix ) only if certain conditions are satisfied (the matrix is invertible), and maybe do something else otherwise (print a warning). This can be done in Python using the if/else construction:
Here the general pattern is:
Note that the indentation (using a Tab
= 4 spaces) is important!
Here CONDITION
is an expressiong evaluating to a bool
, which is either True
or False
. Basic ingredients for such conditions:
A == B
,A != B
for checking equality (or not-equality)A <= B
,A > B
etc for comparisons of two valuesLogical operations:
Cond1 and Cond2
,Cond1 or Cond2
,not Cond1
It is possible to omit the else
part, in which case nothing is done if CONDITION
is not satisfied.
Exercise
Given real parameters of the quadratic equation write some code which prints the set of solutions (which you have to compute yourself, since solving equations only comes later in the lecture).
Hint: It's never too late in life to look at the formula for the solutions of a general quadratic equation.
Solution: (uncomment to see)
Note that we can have an if
-block inside another if
- or else
-block, using double indentation (and so on):
Python warmup: for-loops
Sometimes we want to perform an operation for all in a range of values. This can be accomplished by a for
-loop. As an example, below we compute the sum of the numbers :
The general pattern is:
Above, we have used range(N)
as the ITERABLE
, which outputs the numbers , which is why we had to take range(101)
to sum from to .
Exercise
Count for how many of the numbers the value is negative.
Solution (uncomment to see)
Similarly, we have the variations:
range(N0, N)
for the numbers ,range(N0, N, d)
for the numbers , where is maximal such that
Some more interesting examples:
Since we are not just using Python, but SageMath, we also have some cool iterables, like the symmetric group given by SymmetricGroup(n)
:
For more information about iterables, see this tutorial.
Python warmup: dictionaries
Dictionaries are a useful data structure in Python, which encodes a map from a finite set of objects to some other objects:
We can easily add new assignments to the dictionary (or change old ones):
There is also a connection to the for
-loops we saw above: on the one hand, dictionaries are themselves Iterables
:
On the other hand, similar to the constructions of lists like [k^2 for k in range(10)]
that we already saw, we can also create dictionaries in this way:
Exercise
Create dictionaries
f,g
implementing the maps
Create the dictionary
h
implementing the composition .
Solution (uncomment to see)
Numbers
Last time, we already saw some interesting rings implemented in SageMath:
ZZ
the integersQQ
the rational numbersRR
the real numbers (floating point operations!)CC
the complex numbers (floating point operations!)GF(q)
the finite field with elements
In this section, we will learn more about elements of these rings (commonly known as "numbers") and what we can do with them.
Integers
When we type an expression like 42
in SageMath, this will produce an Integer:
Integer division and remainder
Apart from the usual division a/b
of two Integers (which mostly produces a Rational), we can also use a//b
to compute the largest integer which is at most :
The remainder (or modulus) of this division can be computed with a%b
:
Exercise
Check whether the number is divisible by .
Solution (uncomment to see)
Exercise
Compute the last digits of the integer where the number appears
times, or
times
in the formula for .
Hint 1: Since the number of digits of an integer roughly doubles when taking its square, we can estimate that has more decimal digits than the number of atoms in the universe. Keep in mind that the code you use for solving the exercise must run on a computer which is part of the universe!
Hint 2: If you have ignored Hint 1, you probably at some point want to click on Kernel -> Interrupt
in the menu to stop the computation, and maybe also on Kernel -> Restart
to clear your memory.
Solution (uncomment to see)
Factorization
We can also compute the prime factorization of an integer:
To actually extract the information from this factorization, to use it in further computations, the following conversions are useful:
Exercise
Find the largest such that the number is divisible by .
Solution (uncomment to see)
Conversely, we can look up the primes in the interval using primes(a,b)
:
Oops, this function returns a generator, i.e. an iterable that can be used in a for
loop, without having to first compute all the numbers it will put out:
To just look at the numbers, you can convert this generator object into a list:
Python int vs. SageMath Integer
Remember the exercise from the first lecture to create a multiplication table of the integers from to :
Let's see what happens instead if we wanted to create a division table:
By golly, what happened? It turns out that the integers that range
spits out are actually of type int
in Python, and not of type Integer
:
Therefore, the division above is a division of int
values, which returns a float
:
To repair this, you can convert either numerator or denominator of the fraction into an Integer
:
Thus a nice and mathematically accurate division table can be obtained as follows:
This type of conversion works more generally:
Exercise
An integer is a perfect power if there exist integers with such that .
For the integers print line by line whether they are perfect powers or not, e.g. the output should start like this:
Solution (uncomment to see)
Rational numbers
If you want to do an exact computation with real numbers (e.g. in linear algebra), it is best when you can stay inside the rational numbers, since they have an exact representation as a fraction. Many operations we saw for Integers above work analogously for Rationals:
Some more useful functions (which also work for integers or real numbers):
Exercise
Among the numbers of the form for , which is closest to ?
Hint: Have a variable storing the best approximation you have so far, and when going through all numbers replace the current optimum if one of them comes closer.
Solution (uncomment to see)
Real and complex numbers
We already saw that RR
and CC
are the fields of real and complex numbers, implemented with floating-point arithmetic. In particular, the computations here are no longer exact:
Since we mostly talk about symbolic computations in this course, we won't go deeper into this topic for now, but here are some links where you can find more information:
Algebraic numbers
One nice field in which exact computations are possible is the field of algebraic numbers. These are complex numbers which are a zero of some polynomial with rational coefficients. The unique such polynomial of minimal degree and with leading coefficient is called the minimal polynomial.
Then we can do things like taking roots of an algebraic number.
Even though below it is displayed as a decimal number, behind the scenes it still remembers its exact representation:
Then we can do fun things, like compute an expansion of a real algebraic number as a continued fraction:
This says that If you haven't seen it, it's a fun exercise to prove this!
Exercise
Compute the minimal polynomial and continued fraction of the golden ratio
Solution (uncomment to see)
Finite fields
Given a prime number , there exists the finite field of integers modulo , which has precisely elements. More generally, for a prime power , , there exists a unique field with elements. It is not given by though! Instead it is given as an extension where is a variable and is an irreducible polynomial of degree .
This finite field can be created in SageMath using FiniteField(q)
(or GF(q)
for short).
If we actually need to write elements of , we can use the following line to specify the variable used in the definition:
We can check e.g. that , since , as .
We can also type formulas using standard integers like 17
. Of course by default they give elements of type Integer
, but SageMath is smart enough to convert them to elements of . We are later going to see more about how this works.
And we can check which irreducible polynomial was used to define ; SageMath automatically picks one for us:
Here is a cool exercise using finite fields, which hints at some quite deep mathematics:
Exercise
Given a prime power , let be the set of solutions of the equation
Compute the cardinality by going through all points in and counting how many of them satisfy the equation.
Compute the cardinality for a few more values of and then make a guess how it grows with .
Hint: There is a function in SageMath giving you a list of all prime powers up to . Can you guess its name and confirm with Tab-completion?
Solution: (uncomment to see)
Symbolic expressions
We have already seen in some examples that SageMath can do computations involving formal variables. These happen in the so-called Symbolic Ring, which is denoted by SR
in SageMath.
Creating and comparing symbolic expressions
To get started, we declare some variable names using the function var
.
Then we can ask to perform operations, like expanding the formula we entered above:
We can also try to check whether two formulas are equivalent:
This is not restricted to algebraic equations:
Exercise
Try to check the following identities, some of which are true and some of which are false. Which one does SageMath get wrong?
Solution (uncomment to see)
Substitution
We can make variable substitutions as follows:
Note that the argument of f.subs
is a dictionary, sending variables appearing in f
to their new values. Alternatively, we can treat f
as if it was a function, and call it (but specifying the names of the variables as follows):
Formal sums
We can also evaluate some formal summations, e.g. the famous identity Indeed, to compute we use sum(f,a,a0,a1)
, where a
is a variable and f
is again a symbolic expression.
The answer is again a symbolic expression, so we can e.g. substitute some value for n
or compute a further symbolic sum:
Solving equations
Maybe you have wondered why writing f == g
for two symbolic expressions does not immediately give either True
or False
, but again a symbolic expression:
The reason is that we can now use this expression to state an equation (or a system of equations) that we want to solve:
The second argument is the variable for which we want to solve. To specify multiple equations (or inequalities) we give a list of these as the first argument of solve
:
To get an output that can be used in further computations, we can specify the optional parameter solution_dict=True
to obtain a list of dictionaries giving our solutions:
Finally, we can also solve for multiple variables:
Exercise
Solve the following (systems of) equalities for the variables :
Solution (uncomment to see)
We can also add some assumptions about the variables:
Here is how we get rid of the assumptions again:
Assignments
Exercise
Given a number here are the rules of a game named -Blup:
The participants stand in a circle and count upwards starting from , except that for every number either divisible by or ending on the digit , they have to say "Blup" instead. If you say something wrong or take too long, you are out, and the others start again.
A correct -Blup would start as follows:
Given d
, write a program that prints the first 50 things the players need to say, i.e.
Hint: Recall that given integers a,b
with b
nonzero, you can compute the remainder of the division of a
by b
using a % b
.
Solution: (uncomment to see)
Exercise
The Collatz conjecture states that for the function $$
f : \mathbb{Z}_{\geq 1} \to \mathbb{Z}_{\geq 1}, n \mapsto
\begin{cases}
3n+1 & \text{for $nParseError: KaTeX parse error: Expected 'EOF', got '}' at position 5: odd}̲,\\
n/2 & \text…nParseError: KaTeX parse error: Expected 'EOF', got '}' at position 6: even}̲
\end{cases}
nnf(n)f(f(n))\ldots$ eventually hits the number . Test the Collatz conjecture for the first integers.
Hint: The while
-loop
repeats the following code block until the CONDITION
becomes False
.
Solution (uncomment to see)
Exercise
The Pólya conjecture states that given a natural number , there are among the set at least as many elements with an odd number of prime factors as elements with an even number of prime factors. Here prime factors are counted with multiplicity, i.e. has prime factors according to this definition.
Test the Pólya conjecture for the integers , for an of your choice.
Google the Pólya conjecture.
Solution: (uncomment to see)
Exercise
Given an integer let be the set of points in contained in the triangle spanned by . Or in other words We claim that the function is given by a polynomial in . Compute this polynomial and check your result in a few cases.
Solution (uncomment to see)