{
"cells": [
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# Jupyter notebook\n",
"\n",
"* Notebook interface for Python, Julia, Perl, R, Go, Mathematica, etc, etc.\n",
"* This is a [*markdown cell*](https://www.markdownguide.org/) for text (including weblinks, LaTeX formulas, etc).\n",
"* One can write LaTeX code here: $ \\Gamma(z+1) = z\\, \\Gamma(z)$\n",
"* Next cell is a *code cell*, use **Shift + Enter** for executing it."
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"print(\"Hello World!\")"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# Basic Python\n"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"3**123"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"# Boolean XOR \n",
"True^False"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"# Division versus integer division in Python 3.\n",
"print(1/3)\n",
"print(1//3)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Lists, loops, and ifs ##"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"for w in [\"bim\", \"bum\", \"bam\"]:\n",
" \n",
" word = \"\"\n",
" \n",
" if w == \"bim\":\n",
" word = word + \" BIM BIM\"\n",
" \n",
" elif w == \"bum\":\n",
" word += \" BUM BUM\"\n",
" \n",
" else:\n",
" word += \" BAM BAM !!!\"\n",
" \n",
" word = w + \" \" + word\n",
" print(word)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Functions"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"def factors(n):\n",
" \"\"\"\n",
" An inefficient but simple method for finding the factors of\n",
" an integer number n, omitting n itself.\n",
" \"\"\"\n",
"\n",
" return [i for i in range(1, n//2+1) if n % i == 0]\n",
"\n",
"factors(144)"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"# Help on that function\n",
"?factors"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"def perfects(n):\n",
" \"\"\" Computing perfect numbers less than n, using a previously defined function. \"\"\"\n",
"\n",
" return [i for i in range(1, n) if sum(factors(i)) == i]\n",
"\n",
"perfects(2000)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# SymPy\n",
"Online version: [SymPy Gamma](https://gamma.sympy.org/)\n",
"## Setting up"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"# Start by importing all default objects from sympy\n",
"from sympy import * \n",
"\n",
"#Set up best available printing interface\n",
"init_printing()"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Constants ##"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"I, pi, E, EulerGamma, oo, sqrt(-2), log(-2), S(1)/3, Rational(1, 3)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Symbolic variables"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"beta = symbols('beta')\n",
"z = symbols('z_0:10')\n",
"\n",
"beta, z"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"sin(z[3]) + beta**5"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"By default symbols are **complex valued**. If we do not want them\n",
"to behave as complex numbers, we should specify another behaviour\n",
"using the keywords:\n",
"\n",
"** commutative, complex, imaginary, real, integer, odd, even, prime, composite, zero, nonzero, rational, algebraic, transcendental, irrational, finite, infinite, negative, nonnegative, positive, nonpositive, hermitian, antihermitian\n",
"**"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"x = symbols('x')\n",
"n = symbols('n', integer = True)\n",
"\n",
"sin(pi*x) + cos(pi*n)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Calculus\n",
"Series, limits, derivatives, integrals."
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"x, y, z, t = symbols('x, y, z, t')\n",
"a, b, c = symbols('a, b, c')\n",
"m, n = symbols('m, n', integer = True)\n",
"\n",
"[\n",
"summation(m**3, (m, 1, n)),\n",
"\n",
"summation(1/n**17, (n, 1, oo)),\n",
"\n",
"limit(sin(x)/x, x, 0),\n",
"\n",
"limit(sin(exp(-1/x)+x)/x, x, 0, '+'),\n",
"\n",
"diff(sin(x)**2, x),\n",
"\n",
"diff(exp(x*y), x, 2, y),\n",
"\n",
"integrate(cos(x), x),\n",
"\n",
"integrate(exp(-x**2), (x, -oo, +oo))\n",
"]"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"\"\"\" A table of integrals. \"\"\"\n",
"\n",
"from IPython.display import Math, display\n",
"\n",
"iData=[(sin(x)**2, (x, 0, pi)),\n",
" (t**(z-1)*exp(-t), (t, 0, oo)),\n",
" (exp(-t*x)*log(t), (t, 0, oo)),\n",
" ((1-t)**(S(1)/2)*t**(S(1)/3), (t, 0, 1))]\n",
"\n",
"for d in iData:\n",
" i = Integral(*d)\n",
" result = latex(i) + \" = \" + latex(simplify(i.doit()))\n",
" display(Math(result))"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Some series"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"f1 = log(gamma(x))\n",
"\n",
"f1s = series(f1, x, 0, 8)\n",
"\n",
"result = (latex(f1) + r\"\\\\=\" + latex(f1s) + r\"\\\\=\" \n",
" + latex(f1s.rewrite(zeta))) \n",
"\n",
"display(Math(result))\n",
"\n",
"print('\\n', result)"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"f2 = sin(x**Rational(1, 3) + x**Rational(1, 5))\n",
"\n",
"f2s = series(f2, x, 0, 1.5)\n",
"\n",
"display(Math(latex(f2) + \"=\" + latex(f2s)))"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Some numerics"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"N(pi**E, 1000)"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"Let us sum the following series:\n",
"$$\\sum_{k=1}^{\\infty}\\left(\\frac{1}{k}-\\log(1+\\frac{1}{k})\\right) = \\gamma_E$$"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"k = symbols('k', integer = True)\n",
"\n",
"s1 = N(Sum(1/k - log(1 + 1/k), (k, 1, oo)), 20)\n",
"\n",
"s2 = N(EulerGamma, 50)\n",
"\n",
"print(s1)\n",
"print(s2)\n",
"print(\"%.3g\" %(s1-s2))"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"An inverse Mellin tranform:\n",
"\n",
"\\begin{align}\n",
"\\int_{-\\infty}^\\infty dt\\; \\Gamma\\left(it+\\tfrac{1}{2}\\right) \\pi^{-it} = 2\\pi^\\frac{3}{2} e^{-\\pi}\n",
"\\end{align}"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"i1 = N(Integral(gamma(I*t + S(1)/2)*pi**(-I*t), (t, -oo, +oo)), 20)\n",
"\n",
"i2 = N(2*pi**(S(3)/2)*exp(-pi), 30)\n",
"\n",
"print(i1)\n",
"print(i2)\n",
"print(\"%.3g\" %abs(i1-i2))"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"## Plots"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"%matplotlib inline\n",
"\n",
"plot(*[legendre(i, x) for i in range(1, 5)], (x, -1, 1))"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"from sympy.plotting.plot import *\n",
"\n",
"r, phi = symbols('r, phi')\n",
"a = 20.1\n",
"b = 0.05\n",
"c = 10\n",
"d = 0.35\n",
"\n",
"plot3d_parametric_surface(r*sin(a*r)*(1 + d*r*sin(phi)), \n",
" r*cos(a*r)*(1 + d*r*cos(phi)), \n",
" b*r**c,\n",
" (r, 0, 1), (phi, 0, 2*pi), \n",
" nb_of_points_u = 100, \n",
" nb_of_points_v = 100,\n",
" title = \"Snake\")"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# The Kac table\n",
"Let's do some object-oriented programming. \n",
"\n",
"In 2d CFT, the Kac table is the set of dimension\n",
"$$\n",
"\\Delta_{(r,s)} = \\frac14\\left( \\frac{q}{p}(r^2-1) +\\frac{p}{q}(s^2-1) -2rs\\right) \\quad \\text{with} \\quad \\left\\{\\begin{array}{l} 1\\leq r\\leq p-1 \\\\ 1\\leq s\\leq q-1 \\end{array}\\right.\n",
"$$\n",
"for $p, q$ positive integers."
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"class Kac:\n",
" \n",
" def __init__(self, indices = (3, 4)):\n",
" \n",
" self.indices = indices\n",
" (p, q) = indices\n",
" self.table = [[self.Dimension((r, q-s)) for r in range(1, p)] \n",
" for s in range(1, q)]\n",
" \n",
" def Dimension(self, pair):\n",
" \n",
" (p, q) = self.indices\n",
" (r, s) = pair\n",
" return (S(q)/p*(r**2-1) + S(p)/q*(s**2-1) + 2*(1-r*s))/4\n",
" \n",
" def display(self, source = False): \n",
" \n",
" if source:\n",
" print(latex(Matrix(self.table)))\n",
" else:\n",
" return Matrix(self.table)\n",
" \n",
" def ground_state(self):\n",
" \n",
" return min(sum(self.table, []))"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"myKac = Kac((5, 8))\n",
"\n",
"myKac.Dimension((3, 2))"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"myKac.display()"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"myKac.display(source = True)"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"myKac.ground_state()"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# Schwarzschild black hole"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"from IPython.display import Math,Latex,display\n",
"\n",
"from sympy import *\n",
"from sympy.diffgeom import *\n",
"\n",
"# Let's define our own abbreviations for some useful functions\n",
"TP = TensorProduct\n",
"d = Differential\n",
"LieD = LieDerivative\n",
"\n",
"# A manifold, a patch, and coordinates, with our own names\n",
"m = Manifold('Schwarzschild_4', 4)\n",
"p = Patch('External', m)\n",
"spherical = CoordSystem('Spherical', p, ['t', 'r', 'theta', 'phi'])\n",
"\n",
"# Coordinate, derivatives (vector fields), one-forms\n",
"xs = t, r, theta, phi = spherical.coord_functions()\n",
"es = e_t, e_r, e_theta, e_phi = spherical.base_vectors()\n",
"fs = dt, dr, dtheta, dphi = spherical.base_oneforms()\n",
"\n",
"xs, es, fs"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
" Let's check that $dx^j(\\partial_{x^i}) = \\delta_i^j$"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"pprint(Matrix([[f(e) for f in fs] for e in es]))"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Spherical, stationary ansatz ### \n",
"We introduce a metric that depends on two unknown functions:\n",
"$$\n",
"ds^2 = -A_0(r) dt^2 + A_1(r) dr^2 + r^2(d\\theta^2 + \\sin^2\\theta d\\phi^2)\n",
"$$"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"(A0, A1) = symbols('A_0, A_1', cls = Function)\n",
"\n",
"metric = (-A0(r)*TP(dt, dt) + A1(r)*TP(dr, dr) \n",
" + r**2*(TP(dtheta, dtheta) + sin(theta)**2*TP(dphi, dphi)))\n",
"metric"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"\"\"\" We compute the Ricci tensor, check that its off-diagonal terms \n",
"identically vanish, and write the vanishing of the diagonal terms \n",
"as equations for A_0, A_1. \"\"\"\n",
"\n",
"ricci = metric_to_Ricci_components(metric)\n",
"\n",
"print(\"Off-diagonal terms of the Ricci tensor:\", \n",
" [[ricci[i, j] for i in range(4) if not(i == j)] for j in range(4)])"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"# Technicality: r is a ScalarField, for solving ODE's it is better \n",
"# to replace it by a symbol\n",
"R = symbols('R', Positive = True)\n",
"ricciII = ricci.replace(r, R).doit()\n",
"\n",
"print(\"\\nDiagonal terms of the Ricci tensor:\")\n",
"\n",
"for i in range(4):\n",
" display(Math(\"(\" + str(i) + \")\\quad \" \n",
" + latex(Eq(ricciII[i, i], 0))))"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"### Solving the equations"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"\"\"\" We find that the first two equations have a simple combination \n",
"that can be easily solved. \"\"\"\n",
"\n",
"eq5 = expand( R * A1(R) * (ricciII[0, 0]*A1(R) + ricciII[1, 1]*A0(R)) )\n",
"\n",
"display(Eq(eq5, 0))\n",
"\n",
"sol5 = dsolve(eq5, A1(R), ics = {A1(1):1/A0(1)}) \n",
"# Specifying initial conditions\n",
"\n",
"display(sol5)"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"\"\"\" We plug this solution into the original four equations. \"\"\"\n",
"\n",
"ricciIII = ricciII.replace(sol5.lhs, sol5.rhs).doit()\n",
"\n",
"for i in range(4):\n",
" display(Math(\"(\" + str(i) + \"')\\quad \" \n",
" + latex(Eq(ricciIII[i,i], 0))))"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"\"\"\" We solve (2'), and check that all equations are satisfied. \"\"\"\n",
"\n",
"M = Symbol('M')\n",
"\n",
"sol = dsolve(ricciIII[2,2], A0(R), ics = {A0(M):0})\n",
"\n",
"ricciIV = ricciIII.replace(sol.lhs, sol.rhs).doit()\n",
"\n",
"display(sol)\n",
"\n",
"for i in range(4):\n",
" display(Math(\"(\" + str(i) + \"')\\quad \" \n",
" + latex(Eq(simplify(ricciIV[i, i]), 0))))"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": [
"\"\"\" Computing the metric. \"\"\"\n",
"\n",
"schwMetric = ( metric.replace(r, R).replace(sol5.lhs, sol5.rhs).doit()\n",
" .replace(sol.lhs, sol.rhs).doit() )\n",
"schwMetric"
]
},
{
"cell_type": "markdown",
"metadata": {},
"source": [
"# References #\n",
"\n",
"### References on Python 3.x ###\n",
"\n",
"* Official [Python 3.x documentation](https://docs.python.org/3/), start from the [tutorial](https://docs.python.org/3/tutorial/index.html)\n",
"* [Python documentary resources](https://wiki.python.org/moin/BeginnersGuide/Programmers)\n",
"* [Dive Into Python 3](https://www.diveinto.org/python3/)\n",
"* [www.python-course.eu](https://www.python-course.eu/python3_course.php)\n",
"* [Python 3 Patterns, Recipes and Idioms](https://python-3-patterns-idioms-test.readthedocs.io/en/latest/index.html)\n",
"\n",
"### References on Jupyther and IPython kernel ###\n",
"\n",
"* [Jupyter official site](https://jupyter.org/) \n",
"* [Jupyter notebook docs](https://jupyter-notebook.readthedocs.io/en/stable/)\n",
"* [nbconvert docs](https://nbconvert.readthedocs.io/en/latest/) **nbconvert** converts Jupyter notebooks to other formats\n",
"* [nbconvert examples](https://github.com/jupyter/nbconvert-examples)\n",
"* [nbviewer](https://nbviewer.jupyter.org/) Browse online repository and preview Jupyter notebooks\n",
"\n",
"\n",
"* [IPython kernel](https://ipython.readthedocs.io/en/stable/)\n",
"* [iPyton magic commands](https://ipython.readthedocs.io/en/stable/interactive/magics.html)\n",
"* [IPython example notebooks](https://github.com/ipython/ipython/tree/1.x/examples/notebooks/); [IPython example notebooks via nbviewer](https://nbviewer.jupyter.org/github/ipython/ipython/tree/1.x/examples/notebooks/)\n",
"\n",
"### References on Markdown ###\n",
"\n",
"* [Markdown syntax](https://daringfireball.net/projects/markdown/syntax) Official syntax\n",
"* [markdownguide.org](https://www.markdownguide.org/) Markdown Guide\n",
"\n",
"### References on Sympy ###\n",
"\n",
"* [Sympy documentation (devel)](https://docs.sympy.org/devel/index.html)\n",
"* [Sympy Wiki](https://github.com/sympy/sympy/wiki)\n",
"* [Examples](https://github.com/sympy/sympy/tree/master/examples) Notebooks and Python code from Sympy's repository.\n",
"* [sympy@github](https://github.com/sympy/sympy) Official source code repository\n",
"* [sympy@FOSSIES](https://fossies.org/search?q=folder_search&q1=sympy&rd=%2Ffresh%2F&sd=0&ud=%2F&ap=no&ca=no&dp=0&si=0&sn=1&ml=30&dml=3) Unofficial but nicer-looking code repository\n",
"* [SymPy: symbolic computing in Python](https://peerj.com/articles/cs-103/) Cite this PeerJ article if you use Sympy.\n",
"\n",
"* [Sympy Live (online shell)](https://live.sympy.org/)\n",
"* [Sympy Gamma (ask Sympy!)](https://gamma.sympy.org/)\n",
"\n",
"### References on Numpy ###\n",
"\n",
"* [Numpy](http://www.numpy.org/) [Numpy documentation (devel)](https://www.numpy.org/devdocs)\n",
"\n",
"### References on SciPy ###\n",
"\n",
"* [SciPy](https://www.scipy.org/about.html), [SciPy Library](https://www.scipy.org/scipylib/index.html)\n",
"\n",
"### Plotting in Python ###\n",
"\n",
"* [Sympy's plotting module](https://docs.sympy.org/latest/modules/plotting.html)\n",
"* [matplotlib](https://matplotlib.org/)\n",
"* [plotly](https://plot.ly/python/)\n",
"* [bokeh](http://bokeh.pydata.org/en/latest/docs/gallery.html)"
]
},
{
"cell_type": "code",
"execution_count": null,
"metadata": {},
"outputs": [],
"source": []
}
],
"metadata": {
"kernelspec": {
"display_name": "Python 3",
"language": "python",
"name": "python3"
},
"language_info": {
"codemirror_mode": {
"name": "ipython",
"version": 3
},
"file_extension": ".py",
"mimetype": "text/x-python",
"name": "python",
"nbconvert_exporter": "python",
"pygments_lexer": "ipython3",
"version": "3.7.3rc1"
}
},
"nbformat": 4,
"nbformat_minor": 2
}