This Sage document is one of the tutorials developed for the MAA PREP Workshop “Sage: Using Open-Source Mathematics Software with Undergraduates” (funding provided by NSF DUE 0817071). It is licensed under the Creative Commons Attribution-ShareAlike 3.0 license (CC BY-SA).
This tutorial has the following sections:
It assumes that one is familiar with the absolute basics of functions and evaluation in Sage. We provide a (very) brief refresher.
sage: f(x)=x^3+1 sage: f(2) 9
In the first tutorial, we defined functions using notation similar to that one would use in (say) a calculus course.
There is a useful variant on this - defining expressions involving variables. This will give us the opportunity to point out several important, and sometimes subtle, things.
In the cell below, we define an expression \(FV\) which is the future value of an investment of $100, compounded continuously. We then substitute in values for \(r\) and \(t\) which calculate the future value for \(t=5\) years and \(r=5\%\) nominal interest.
sage: var('r,t') (r, t) sage: FV=100*e^(r*t)
sage: FV(r=.05,t=5) 128.402541668774
The previous cells point out several things to remember when working with symbolic expressions. Some are fairly standard.
- Although it is possible to allow implicit multiplication, this can easily lead to ambiguity.
- Of course, if you redefine \(e\) to be something else, all bets are off!
However, two others may be unfamiliar, especially if you have not used much mathematical software before.
- We did that above by typing var('r,t').
- This is automatically done with the \(f(x)\) notation, but without that it is necessary, so that Sage knows one intends t (for instance) is a symbolic variable and not a number or something else.
- For instance, above we used FV(r=.05,t=5) to indicate the precise values of \(r\) and \(t\).
Notice that when we define a function, we don’t need to specify which variable has which value. In the function defined below, we have already specified an order.
sage: FV2(r,t)=100*e^(r*t) sage: FV2(.05,5) 128.402541668774
In this case it is clear that \(r\) is first and \(t\) is second.
But with FV=100*e^(r*t), there is no particular reason \(r\) or \(t\) should be first.
sage: FV(r=.05,t=5); FV(t=5,r=.05) 128.402541668774 128.402541668774
This is why we receive a deprecation error message when we try to do \(FV\) without explicitly mentioning the variables.
sage: FV(5,.05) doctest:...: DeprecationWarning: Substitution using function-call syntax and unnamed arguments is deprecated and will be removed from a future release of Sage; you can use named arguments instead, like EXPR(x=..., y=...) See http://trac.sagemath.org/5930 for details. 128.402541668774
In this case, the outcome is the same, since \(rt=tr\)! Of course, in most expressions, one would not be so lucky, as the following example indicates.
sage: y = var('y') sage: G = x*y^2 sage: G(1,2); G(2,1) 4 2
Also remember that when we don’t use function notation, we’ll need to define our variables.
One of the great things we can do with expressions is manipulate them. Let’s make a typical expression.
sage: z = (x+1)^3
In the cells below, you’ll notice something new: the character #. In Sage (and in Python ), anything on a single line after the number/pound sign (the octothorp ) is ignored. We say that # is a comment character. We use it below to mention alternative ways to do the same thing.
sage: expand(z) # or z.expand() x^3 + 3*x^2 + 3*x + 1
sage: y = expand(z) sage: y.factor() # or factor(y) (x + 1)^3
In the previous cell, we assigned the expression which is the expansion of \(z\) to the variable \(y\) with the first line. After that, anything we want to do to the expansion of \(z\) can be done by doing it to \(y\).
There are more commands like this as well. Notice that \(z\) will no longer be \((x+1)^3\) after this cell is evaluated, since we’ve assigned \(z\) to a (much more complex) expression.
sage: z = ((x - 1)^(3/2) - (x + 1)*sqrt(x - 1))/sqrt((x - 1)*(x + 1)) sage: z.simplify_full() -2/sqrt(x + 1)
sage: z.simplify_rational() # Just simplify the fraction part of the expression by combining it. -2*sqrt(x - 1)/sqrt(x^2 - 1)
This is a good place for a few reminders of basic help.
sage: z.simplify <built-in method simplify of sage.symbolic.expression.Expression object at ...>
Finally, recall that you can get nicely typeset versions of the output in several ways.
Another Sage command that is useful in this context is solve.
Here, we solve the simple equation \(x^2=-1\).
sage: solve(x^2==-1,x) # solve x^2==-1 for x [x == -I, x == I]
- This is because the single equals sign means assignment to a variable, as we’ve done above, so Sage (along with Python) uses the double equals sign for symbolic equality.
It’s also possible to solve more than one expression simultaneously.
sage: solve([x^2==1,x^3==1],x) [[x == 1]]
One of the other basic uses of mathematics software is easy plotting. Here, we include a brief introduction to the sorts of plotting which will prepare us to use Sage in calculus. (There will be a separate tutorial for more advanced plotting techniques.)
Recall that we can generate a plot using fairly simple syntax. Here, we define a function of \(x\) and plot it between \(-1\) and \(1\).
sage: f(x)=x^3+1 sage: plot(f,(x,-1,1))
We can give the plot a name, so that if we want to do something with the plot later, we don’t have to type out the entire plot command. Remember, this is called assigning the plot to the name/variable.
In the next cell, we give the plot the name \(P\).
One plot is nice, but one might want to superimpose plots as well. For instance, the tangent line to \(f\) at \(x=0\) is just the line \(y=1\), and we might want to show this together with the plot.
So let’s plot this line in a different color, and with a different style for the line, but over the same interval.
sage: Q=plot(1,(x,-1,1),color="red", linestyle="--") sage: Q
Because we put \(Q\) in a line by itself at the end, it shows. We were able to use just one cell to define \(Q\) and show it, by putting each command in a separate line in the same input cell.
Now to show the plots superimposed on each other, we simply add them.
Suppose we wanted to view a detail of this.
Since the axes no longer cross in the frame of reference, Sage shows a short gap between the horizontal and vertical axes.
There are many options one can pass in for various purposes.
- Such as the color option when we made a "red" line.
- Such as the xmin in the previous plot, where the minimum x value was just \(-.1\)
Usually (though not always) quotes are required for option values which are words or strings of characters, and not required for numerical values.
Two of the most useful of these options help in labeling graphs.
- As with the word processor, we can use dollar signs (like in LaTeX) to make the labels typeset nicely.
- Here we need both quotes and brackets for proper syntax, since there are two axes to label and the labels are not actually numbers.
- LaTeX notation works here too.
- In the graphic above, we needed to explicitly ask to show the label. With multiple graphs this should not be necessary.
sage: P1 = plot(f,(x,-1,1),axes_labels=['$x$','$y$'],legend_label='$f(x)$') sage: P2 = plot(sin,(x,-1,1),axes_labels=['$x$','$y$'],legend_label='$\sin(x)$',color='red') sage: P1+P2
One additional useful note is that plots of functions with vertical asymptotes may need their vertical viewing range set manually; otherwise the asymptote may really go to infinity!
Remember, you can use the command plot? to find out about most of the options demonstrated above.
Below, you can experiment with several of the plotting options.
sage: x = var('x') sage: @interact sage: def plot_example(f=sin(x^2),r=range_slider(-5,5,step_size=1/4,default=(-3,3)), ... color=color_selector(widget='colorpicker'), ... thickness=(3,(1..10)), ... adaptive_recursion=(5,(0..10)), adaptive_tolerance=(0.01,(0.001,1)), ... plot_points=(20,(1..100)), ... linestyle=['-','--','-.',':'], ... gridlines=False, fill=False, ... frame=False, axes=True ... ): ... show(plot(f, (x,r,r), color=color, thickness=thickness, ... adaptive_recursion=adaptive_recursion, ... adaptive_tolerance=adaptive_tolerance, plot_points=plot_points, ... linestyle=linestyle, fill=fill if fill else None), ... gridlines=gridlines, frame=frame, axes=axes)
There are several mechanisms for viewing three-dimensional plots in Sage, but we will stick to the default option in the notebook interface, which is via Java applets from the program Jmol .
Plotting a 3D plot is similar to plotting a 2D plot, but we need to specify ranges for two variables instead of one.
sage: g(x,y)=sin(x^2+y^2) sage: plot3d(g,(x,-5,5),(y,-5,5))
There is a lot you can do with the 3D plots.
- spinning the plot,
- changing various colors,
- and even making the plot suitable for viewing through 3D glasses (under the “style”, then “stereographic” submenus),
When using the plot3d command, the first variable range specified is plotted along the usual “x” axis, while the second range specified is plotted along the usual “y” axis.
The plot above is somewhat crude because the function is not sampled enough times - this is fairly rapidly changing function, after all. We can make the plot smoother by telling Sage to sample the function using a grid of 300 by 300 points. Sage then samples the function at 90,000 points!
As with 2D plots, we can superimpose 3D plots by adding them together.
Note that in this one, we do not define the functions, but only use expressions (see the first set of topics in this tutorial), so it is wisest to define the variables ahead of time.
sage: var('x,y') (x, y) sage: b = 2.2 sage: P=plot3d(sin(x^2-y^2),(x,-b,b),(y,-b,b), opacity=.7) sage: Q=plot3d(0, (x,-b,b), (y,-b,b), color='red') sage: P+Q
As usual, only the last command shows up in the notebook, though clearly all are evaluated. This also demonstrates that many of the same options work for 3D plots as for 2D plots.
We close this tutorial with a cool plot that we define implicitly as a 3D contour plot.
sage: var('x,y,z') (x, y, z) sage: T = golden_ratio sage: p = 2 - (cos(x + T*y) + cos(x - T*y) + cos(y + T*z) + cos(y - T*z) + cos(z - T*x) + cos(z + T*x)) sage: r = 4.78 sage: implicit_plot3d(p, (x, -r, r), (y, -r, r), (z, -r, r), plot_points=50, color='yellow')
The next tutorial will use all that you have learned about Sage basics, symbolics, and plotting in a specific mathematical venue - the calculus sequence!