{ "cells": [ { "cell_type": "markdown", "metadata": {}, "source": [ "**Math - Linear Algebra**\n", "\n", "*Linear Algebra is the branch of mathematics that studies [vector spaces](https://en.wikipedia.org/wiki/Vector_space) and linear transformations between vector spaces, such as rotating a shape, scaling it up or down, translating it (i.e. moving it), etc.*\n", "\n", "*Machine Learning relies heavily on Linear Algebra, so it is essential to understand what vectors and matrices are, what operations you can perform with them, and how they can be useful.*" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "\n", " \n", " \n", "
\n", " \"Open\n", " \n", " \n", "
" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "# Vectors\n", "## Definition\n", "A vector is a quantity defined by a magnitude and a direction. For example, a rocket's velocity is a 3-dimensional vector: its magnitude is the speed of the rocket, and its direction is (hopefully) up. A vector can be represented by an array of numbers called *scalars*. Each scalar corresponds to the magnitude of the vector with regards to each dimension.\n", "\n", "For example, say the rocket is going up at a slight angle: it has a vertical speed of 5,000 m/s, and also a slight speed towards the East at 10 m/s, and a slight speed towards the North at 50 m/s. The rocket's velocity may be represented by the following vector:\n", "\n", "**velocity** $= \\begin{pmatrix}\n", "10 \\\\\n", "50 \\\\\n", "5000 \\\\\n", "\\end{pmatrix}$\n", "\n", "Note: by convention vectors are generally presented in the form of columns. Also, vector names are usually lowercase to distinguish them from matrices (which we will discuss below) and in bold (when possible) to distinguish them from simple scalar values such as ${meters\\_per\\_second} = 5026$.\n", "\n", "A list of N numbers may also represent the coordinates of a point in an N-dimensional space, so it is quite frequent to represent vectors as simple points instead of arrows. A vector with 1 element may be represented as an arrow or a point on an axis, a vector with 2 elements is an arrow or a point on a plane, a vector with 3 elements is an arrow or a point in space, and a vector with N elements is an arrow or a point in an N-dimensional space… which most people find hard to imagine.\n", "\n", "\n", "## Purpose\n", "Vectors have many purposes in Machine Learning, most notably to represent observations and predictions. For example, say we built a Machine Learning system to classify videos into 3 categories (good, spam, clickbait) based on what we know about them. For each video, we would have a vector representing what we know about it, such as:\n", "\n", "**video** $= \\begin{pmatrix}\n", "10.5 \\\\\n", "5.2 \\\\\n", "3.25 \\\\\n", "7.0\n", "\\end{pmatrix}$\n", "\n", "This vector could represent a video that lasts 10.5 minutes, but only 5.2% viewers watch for more than a minute, it gets 3.25 views per day on average, and it was flagged 7 times as spam. As you can see, each axis may have a different meaning.\n", "\n", "Based on this vector our Machine Learning system may predict that there is an 80% probability that it is a spam video, 18% that it is clickbait, and 2% that it is a good video. This could be represented as the following vector:\n", "\n", "**class_probabilities** $= \\begin{pmatrix}\n", "0.80 \\\\\n", "0.18 \\\\\n", "0.02\n", "\\end{pmatrix}$" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Vectors in python\n", "In python, a vector can be represented in many ways, the simplest being a regular python list of numbers:" ] }, { "cell_type": "code", "execution_count": 1, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "[10.5, 5.2, 3.25, 7.0]" ] }, "execution_count": 1, "metadata": {}, "output_type": "execute_result" } ], "source": [ "[10.5, 5.2, 3.25, 7.0]" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Since we plan to do quite a lot of scientific calculations, it is much better to use NumPy's `ndarray`, which provides a lot of convenient and optimized implementations of essential mathematical operations on vectors (for more details about NumPy, check out the [NumPy tutorial](tools_numpy.ipynb)). For example:" ] }, { "cell_type": "code", "execution_count": 2, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([10.5 , 5.2 , 3.25, 7. ])" ] }, "execution_count": 2, "metadata": {}, "output_type": "execute_result" } ], "source": [ "import numpy as np\n", "\n", "video = np.array([10.5, 5.2, 3.25, 7.0])\n", "video" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The size of a vector can be obtained using the `size` attribute:" ] }, { "cell_type": "code", "execution_count": 3, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "4" ] }, "execution_count": 3, "metadata": {}, "output_type": "execute_result" } ], "source": [ "video.size" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The $i^{th}$ element (also called *entry* or *item*) of a vector $\\textbf{v}$ is noted $\\textbf{v}_i$.\n", "\n", "Note that indices in mathematics generally start at 1, but in programming they usually start at 0. So to access $\\textbf{video}_3$ programmatically, we would write:" ] }, { "cell_type": "code", "execution_count": 4, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "3.25" ] }, "execution_count": 4, "metadata": {}, "output_type": "execute_result" } ], "source": [ "video[2] # 3rd element" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Plotting vectors\n", "To plot vectors we will use matplotlib, so let's start by importing it (for details about matplotlib, check the [matplotlib tutorial](tools_matplotlib.ipynb)):" ] }, { "cell_type": "code", "execution_count": 5, "metadata": {}, "outputs": [], "source": [ "import matplotlib.pyplot as plt" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### 2D vectors\n", "Let's create a couple of very simple 2D vectors to plot:" ] }, { "cell_type": "code", "execution_count": 6, "metadata": {}, "outputs": [], "source": [ "u = np.array([2, 5])\n", "v = np.array([3, 1])" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "These vectors each have 2 elements, so they can easily be represented graphically on a 2D graph, for example as points:" ] }, { "cell_type": "code", "execution_count": 7, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "x_coords, y_coords = zip(u, v)\n", "plt.scatter(x_coords, y_coords, color=[\"r\",\"b\"])\n", "plt.axis([0, 9, 0, 6])\n", "plt.grid()\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Vectors can also be represented as arrows. Let's create a small convenience function to draw nice arrows:" ] }, { "cell_type": "code", "execution_count": 8, "metadata": {}, "outputs": [], "source": [ "def plot_vector2d(vector2d, origin=[0, 0], **options):\n", " return plt.arrow(origin[0], origin[1], vector2d[0], vector2d[1],\n", " head_width=0.2, head_length=0.3, length_includes_head=True,\n", " **options)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Now let's draw the vectors **u** and **v** as arrows:" ] }, { "cell_type": "code", "execution_count": 9, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "plot_vector2d(u, color=\"r\")\n", "plot_vector2d(v, color=\"b\")\n", "plt.axis([0, 9, 0, 6])\n", "plt.grid()\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### 3D vectors\n", "Plotting 3D vectors is also relatively straightforward. First, let's create two 3D vectors:" ] }, { "cell_type": "code", "execution_count": 10, "metadata": {}, "outputs": [], "source": [ "a = np.array([1, 2, 8])\n", "b = np.array([5, 6, 3])" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Now let's plot them using matplotlib's `Axes3D`:" ] }, { "cell_type": "code", "execution_count": 11, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "subplot3d = plt.subplot(111, projection='3d')\n", "x_coords, y_coords, z_coords = zip(a,b)\n", "subplot3d.scatter(x_coords, y_coords, z_coords)\n", "subplot3d.set_zlim3d([0, 9])\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "It is a bit hard to visualize exactly where in space these two points are, so let's add vertical lines. We'll create a small convenience function to plot a list of 3d vectors with vertical lines attached:" ] }, { "cell_type": "code", "execution_count": 12, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "def plot_vectors3d(ax, vectors3d, z0, **options):\n", " for v in vectors3d:\n", " x, y, z = v\n", " ax.plot([x,x], [y,y], [z0, z], color=\"gray\", linestyle='dotted', marker=\".\")\n", " x_coords, y_coords, z_coords = zip(*vectors3d)\n", " ax.scatter(x_coords, y_coords, z_coords, **options)\n", "\n", "subplot3d = plt.subplot(111, projection='3d')\n", "subplot3d.set_zlim([0, 9])\n", "plot_vectors3d(subplot3d, [a,b], 0, color=(\"r\",\"b\"))\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Norm\n", "The norm of a vector $\\textbf{u}$, noted $\\left \\Vert \\textbf{u} \\right \\|$, is a measure of the length (a.k.a. the magnitude) of $\\textbf{u}$. There are multiple possible norms, but the most common one (and the only one we will discuss here) is the Euclidian norm, which is defined as:\n", "\n", "$\\left \\Vert \\textbf{u} \\right \\| = \\sqrt{\\sum_{i}{\\textbf{u}_i}^2}$\n", "\n", "That's the square root of the sum of all the squares of the components of $\\textbf{u}$. We could implement this easily in pure python, recalling that $\\sqrt x = x^{\\frac{1}{2}}$" ] }, { "cell_type": "code", "execution_count": 13, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "|| [2 5] || =\n" ] }, { "data": { "text/plain": [ "5.385164807134504" ] }, "execution_count": 13, "metadata": {}, "output_type": "execute_result" } ], "source": [ "def vector_norm(vector):\n", " squares = [element**2 for element in vector]\n", " return sum(squares)**0.5\n", "\n", "print(\"||\", u, \"|| =\")\n", "vector_norm(u)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "However, it is much more efficient to use NumPy's `norm` function, available in the `linalg` (**Lin**ear **Alg**ebra) module:" ] }, { "cell_type": "code", "execution_count": 14, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "5.385164807134504" ] }, "execution_count": 14, "metadata": {}, "output_type": "execute_result" } ], "source": [ "import numpy.linalg as LA\n", "\n", "LA.norm(u)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Let's plot a little diagram to confirm that the length of vector $\\textbf{u}$ is indeed $\\approx5.4$:" ] }, { "cell_type": "code", "execution_count": 15, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "radius = LA.norm(u)\n", "plt.gca().add_artist(plt.Circle((0,0), radius, color=\"#DDDDDD\"))\n", "plot_vector2d(u, color=\"red\")\n", "plt.axis([0, 8.7, 0, 6])\n", "plt.gca().set_aspect(\"equal\")\n", "plt.grid()\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Looks about right!" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Addition\n", "Vectors of same size can be added together. Addition is performed *elementwise*:" ] }, { "cell_type": "code", "execution_count": 16, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ " [2 5]\n", "+ [3 1]\n", "----------\n" ] }, { "data": { "text/plain": [ "array([5, 6])" ] }, "execution_count": 16, "metadata": {}, "output_type": "execute_result" } ], "source": [ "print(\" \", u)\n", "print(\"+\", v)\n", "print(\"-\"*10)\n", "u + v" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Let's look at what vector addition looks like graphically:" ] }, { "cell_type": "code", "execution_count": 17, "metadata": { "scrolled": true }, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "plot_vector2d(u, color=\"r\")\n", "plot_vector2d(v, color=\"b\")\n", "plot_vector2d(v, origin=u, color=\"b\", linestyle=\"dotted\")\n", "plot_vector2d(u, origin=v, color=\"r\", linestyle=\"dotted\")\n", "plot_vector2d(u+v, color=\"g\")\n", "plt.axis([0, 9, 0, 7])\n", "plt.gca().set_aspect(\"equal\")\n", "plt.text(0.7, 3, \"u\", color=\"r\", fontsize=18)\n", "plt.text(4, 3, \"u\", color=\"r\", fontsize=18)\n", "plt.text(1.8, 0.2, \"v\", color=\"b\", fontsize=18)\n", "plt.text(3.1, 5.6, \"v\", color=\"b\", fontsize=18)\n", "plt.text(2.4, 2.5, \"u+v\", color=\"g\", fontsize=18)\n", "plt.grid()\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Vector addition is **commutative**, meaning that $\\textbf{u} + \\textbf{v} = \\textbf{v} + \\textbf{u}$. You can see it on the previous image: following $\\textbf{u}$ *then* $\\textbf{v}$ leads to the same point as following $\\textbf{v}$ *then* $\\textbf{u}$.\n", "\n", "Vector addition is also **associative**, meaning that $\\textbf{u} + (\\textbf{v} + \\textbf{w}) = (\\textbf{u} + \\textbf{v}) + \\textbf{w}$." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "If you have a shape defined by a number of points (vectors), and you add a vector $\\textbf{v}$ to all of these points, then the whole shape gets shifted by $\\textbf{v}$. This is called a [geometric translation](https://en.wikipedia.org/wiki/Translation_%28geometry%29):" ] }, { "cell_type": "code", "execution_count": 18, "metadata": {}, "outputs": [ { "data": { "image/png": "iVBORw0KGgoAAAANSUhEUgAAASMAAAD8CAYAAAA8P8JjAAAAOXRFWHRTb2Z0d2FyZQBNYXRwbG90bGliIHZlcnNpb24zLjQuMywgaHR0cHM6Ly9tYXRwbG90bGliLm9yZy/MnkTPAAAACXBIWXMAAAsTAAALEwEAmpwYAAAtZElEQVR4nO2deXhU5dn/P082SMIuAVkkCBhAUQQRxRWpUixYq61vUWrR1salWLfWKrS2b63dXOpLX61FtJRXtK5UpWr1V4JIZZFVUYgQlhDAsC8hA5nJPL8/7hyIIcskmTPnnMn9ua65Mpk5c86XYeab+7nv534eY61FURTFa1K8FqAoigJqRoqi+AQ1I0VRfIGakaIovkDNSFEUX6BmpCiKL0iL5SBjzCbgIFAJRKy1w9wUpShKyyMmM6riEmvtLteUKIrSotFhmqIovsDEMgPbGLMR2AtY4C/W2mm1HJMP5AO0bt36rF69esVZqjtEo1FSUoLjyUHSGyStECy9QdIK8Pnnn++y1ubUe5C1tsEb0L3qZxdgFXBRfcfn5eXZoFBQUOC1hEYRJL1B0mptsPQGSau11gJLbQM+E5O1Wmu3Vf3cAcwGhjfdIxVFUY6nQTMyxmQbY9o694HRwGq3hSmK0rKIpZrWFZhtjHGOf95a+46rqhRFaXE0aEbW2g3A4ARoURSlBROcdLyiKEmNmpGiKL5AzUhRFF+gZqQoii9QM1IUxReoGSmK4gvUjBRF8QVqRoqi+AI1I0VRfIGakaIovkDNSFEUX6BmpCiKL1AzUhTFF6gZKYrCrFnQuzekpMjPWbMSr6Exu4MoipKEzJoF+flQXi6/b94svwNMmJA4HRoZKUqy8sknsHCh3J89G3buhP374cUX5bHly2HpUqZMOWZEDuXlMGVKYuVqZKQoycb778P48VBRAdZCZiYcPCg/jYFDh+Duu+HwYbCW4r27qC0uKS5OrGw1I0VJNoYOhauvhieflN/37pWfBw8eO6asDIAK0mltjhCymcedJtG7jekwTVGSjbZtYfToBg+rIJ3xvRcTspnU3IItKwseesglfXWgZqQoyUgoBDl175lYkdWB8V3nMXvTEKZOhbFj5XFjIDcXpk1LbPIa1IwU5SidFi+Wb+PUqbUfMGKEfMHD4cQKi5WyMti3T/JB115bp5tUDBrK+POLmV16HlOnwu23Q1oaDBgA0Shs2pR4IwI1I0U5yp5hw6BbN5g58/gn162DRYvguusgPT3x4upi1y54+21Yu1aGZ889B7fdJo7Stu1xh1eMHsf4VrOZ/V7bo0YE8vL+/RMrvSZqRorikJoqIcGyZfDZZ19+zjGoiRMTr6smhw7BF1/A4sUwaRJ87WvQr5+U7SdNkvu5uXDFFXDSSfKa1q2pmPxLxme/yexlvb5kRJEIrF8vkZGXqBkpSnUcs6keHVkrEcegQVKp8ooZM+Cb34Rt22D7dskLvfCC6EtLg3btvnz82WfDJZfAsGFUvPom4z+ezOzZfMmIQIKocFgjI0XxF4MGwZAhMi05GpXH5s+Xb2yioyJr5brt28Pzz0tO6MQTJfIZMgRGjpQcV3106kTFg79n/PRLmT0n/TgjAhmigZqRoviPiROhpATmzpXfZ848NoRzm/JyGYZdc400irVqBXfdBZddJkOwJ55o2ICqUfH7PzJ+2qhaIyKHwkL5qWakKH7DSVLPnClDoVdeETPo1s2d6+3YAR9+KK0b2dnwj3/AAw9AUZFc85e/rLdMXxcVFTIRuz4jAomMOneGE05o1r+i2egMbEWpSU4OXH45vPYaXHQRHDgQ/yHawYPw1FOSfL7hBum9KCmR2dIdOjT79LEaEUhk5HXyGjQyUpTamThRhkv33CM5myuvjM95H38c7rwTVq+GyZPlGkuWQGmpRGMJNiIQM/J6iAZqRopSO+PGQadOEhVdc400mTYFa2HNGjnXe+9J53xGhkygDIdh+PBG5YAaorFGtHevjBL9YEY6TFOU2sjIgN27m/baUEgS3hddBFu3SiL81ltlWsBll8VXZzUaa0RwLHnth2GampGixIPSUol6ioul0eutt+CPf4SuXaFPH9e7TptiROCfShqoGSlK0zlwAKZPl+U6Tj9dwov335eIqlOnhMloqhGBVNLS0uDkk93TFytqRorSWH71K8khDRggCe7Ro6VBNTVVns/KSpiU5hgRSGTUr58/2u00ga0osbBsGXTpIku1rlsnDV1XXCEJ6kGDjhlRAmmuEYE/GmQdYjYjY0yqMWaFMWaOm4IUxReEQtIOctJJcOml8tiNN8p45v/+D+6/31N54bBpthH5pUHWoTHDtDuANUC7hg5UlEASicis50WL4DvfkVnR06bBwIGyf89ZZ3mtEJCI6MEHT+WDD5puROCfBlmHmMzIGNMTGAs8BNztqiJFSST798Pf/iYtIKtWyazo6dNl8k0TWjDcxhmaffBBTrOMCPzTIOsQa2T0OHAvcPxqTVUYY/KBfICcnBzmzZvXXG0JoaysLDBaIVh6fa112zZpQgUJD5Yvpywvj3lnnQUrV3oqrS7CYVMVEeWQn7+a00/fRXPe3rfe6gn0Y+fOBcybF4mXzKZjra33BowDnqy6PxKY09Br8vLybFAoKCjwWkKjCJJe32ldsMDabt2s3bjR2osusvapp770tO/0VuPIEWuvuspasHbq1Phovekmazt3br62WACW2gZ8I5YE9vnA140xm4C/A6OMMc+54oyKEk+OHJE8UNu2skVqOCxrQ59wgswHuvlmrxXGRDyqZrXhlwZZhwaHadba+4H7AYwxI4EfW2u/464sRWkie/fKmkCvvw4//KF84/7yF7jwQqmMjRzptcJG4ZYRgbw1V1wRv/M1F51npASfffvg6aePzXx++GH41rdknei8PElOO2tBBwg3jchPDbIOjZqBba2dB8xzRYmiNIaKCun3GjJEykL33w/f+IZs2ewkpgOMm0YE/mqQddDISAkW770Hp5wif9qfe07yQPfdJzOhc3LUiGLETw2yDtqbpvibcFiinc6dYcoUOPNM6Ypv21YmKCYZiTAi8FeDrIOakeI/DhyQSthTT8la0Nu2wSOPyDY93bvD17/utUJXSJQRgb8aZB10mKb4g9274eWXYcsWWeb16aeP7dLRrZt8M7t391qlayTSiMBfDbIOGhkp3hEKScRz3nnwxhvyLSwvl/3BsrO9VpcwEm1EToOs3wJMjYyUxPPKK3D++bBnDzz6qOSF/ud/JAmdmalG5DJ+a5B10MhIcZ/KSlmStV8/mQPUtq0kort0kTlCLRQvjAj81yDroJGR4g5lZWJCkyZJ2SYtTUrw3/ymLM/xxBP+yp4mGK+MCPxZ1gc1IyWe7NwJ774Ln3wi0c+ePXDHHTIu6NwZfvYziYZaOF4aEYgZ+WEH2ZroME1pHocOyTfq0ktlRvQ//ynzgvbtgxUrZIKichSvjQhkmOanmdcOGhkpTWP6dOmA37xZ9oIPheQbFg7LetDt23ut0Hf4wYjAPzvI1kQjIyU2rIWNG6UXbPp0yQl17ixLsh454rU63+MXI/Jjg6yDmpFSN+Xl8vPaa2UeUEmJ5IBGjvTlkqx+xS9GBP5skHXQYVoLZlZpKb0XLiRl3jx6L1zIrNJS+bO5ZAnMny/zfd54Ax58UPrAevSQPcPUiGLGT0YE/q2kgUZGLZZZpaXkFxZSHo0CsPnIEfLXrIEZM5jw73+L+ezdCx06eCs0wPjNiECS1+np/mqQddDIqIUyZcOGo0bkUA5Muflm6Q/LyFAjagZ+NCKQyKhvX39O8VIzaqEU15F0rutxJXb8akTgzwZZBzWjFkgkGiUzpfb/+l5JsDiZl/jZiPy2g2xN1IxaGJFolOvWrKE8GiXdmC89l5WSwkN9+nikLPj42YjAvw2yDmpGLYwKa9kZDvNI3778b79+Rx/PbdWKaf37M6FrVw/VBRe/GxH4t0HWQatpLYRINMrhaJQ2aWm8d8YZpKWksHD/fgDeGDSIKzp39lhhcAmCEYG/y/qgkVGLwBmajfn4Y8LRKGlV+aLCqkmNA7KyvJQXaIJiRODfBlkHNaMkxzGil3fu5KqcHNKrJa7XlpeTbgwnt27tocLgEiQjAv82yDroMC2JqW5Ej/Ttyz01NjK8rmtXTm/T5mikpMRO0IwI/LeDbE3UjJKYu4qK6jQigDPatOGMNm08UBZsgmhEfm6QdVAzSmJ+1KMHp2VlcUuPHsc9F4lGeXP3bka0a8eJOrcoZoJoRODvBlkHjc+TjEg0yozt27HWckodRgSw8fBhrv70U97ZsyfBCoNLUI0I/F9JAzWjpMLJEd1YWMjcBha610pa4wiyEYG/G2Qd1IyShJrJ6q907Fjv8WurzKi/mlGDBN2IwN8Nsg5qRklAQ1Wz2igMhchJT6ejnz+dPiAZjAj8u9RsddSMkoDlZWX8Y9eumI0IZJimQ7T6SRYjikRg3Tp/J69Bq2mBxlqLMYbh7dqxdvhw+mRmxvzavw4YwKHKShfVBZtkMSLwf4Osg0ZGASUSjTJhzRpeKC0FaJQRAfTNzNQ5RnWQTEYE/m+QdVAzCiBOjuiFHTvYVlHR6NcXhUJMLSlhZxNem+wkmxFBMMr6EIMZGWNaG2OWGGNWGWM+Ncb8dyKEKbVTCUeT1Q/36RNzjqg68/ft447169kXicRfYACZNQt694ZRoy6mQ4fkMiLwf4OsQyw5oyPAKGttmTEmHVhgjHnbWrvIZW1KDSqt5UHg/Soj+nGvXk06T6E2yB5l1izIz3d2ZTKEQlL+7tTJa2Xxw+8Nsg4NRkZWKKv6Nb3qZl1VpdRKCtATmmVEIGX9fpmZyd0gu2ULHDggm09+9pk8tm8fbN0q9zdvhrIypky2R7eHcwiHYcqUhKp1lSCU9SHGapoxJhVYBvQDnrDWLq7lmHwgHyAnJ4d58+bFUaZ7lJWV+V5rJVAKdAfGl5XRZsMG5m3Y0OTzLQd6gev/bk/e2927YdcucZT0dLkdOACLFsljkQhkZkoolJFBcfEPaj1NcbFl3rz3E6u9EcT63h48mMaOHReQllbEvHlb3BfWHKy1Md+ADkABMKi+4/Ly8mxQKCgo8FpCvYQrK+01q1fbnAUL7K6KimbrjUSjNmPePPvT9evjI7AePHlvP/zQ2t69rZWYqMFbblpJrU/l5iZeemOI9b1duFD+PW+84a6ehgCW2gb8pVFxurV2HzAPGBNfS1Rqo/rM6ntPOokT4jBbOtUY9lxwAT9txjDP14wYAd/+dmzHXnghD12/hppzP7Oy4KGH4i/NC4JSSYPYqmk5xpgOVfczgUuBtS7ravFUN6Lm5ohqkp2amtxtICtW1P98Rgbcey/Mn8+EZy9l2jTIzQUnFXrffTBhgusqE0IQGmQdYomMugEFxpiPgY+A96y1c9yVpTyyZYsrRvT6rl3cW1REpU3CGoS1MHYs9OhRdygwaBC88ALcc8/RhyZMkFnKc+YsoEsX+Ne/5FTJQBAaZB1iqaZ9bK0dYq09w1o7yFr7q0QIa+nc0bMnL556alyNCGDO7t387YsvSK2xZ1ogsRYOHoR33gFjYMECuPRS+OY3azej3r3hT3+Cq6+GLl2Oezo7u5KHHoL//Adeesl9+YkgKJU00BnYviISjfKLjRvZFw6TmZrKf9XyhWkuheXlwV42xFpYsgTKyiAlRcxn4EAxpPPPh7vukuio+maU6enw9NPSLTpyZL2nv/FGOPNMGcWFQq7+S1wnKA2yDtoo6xOq54hOyczkOyee6Mp11paXc2XQ9kizFt58UzLLRUVwyy2wciUUF8uQLCXFSfoc47HH4O23JT905ZXwjW9AWsMf99RU+OMf4ZJL5BRBnm8UlAZZB42MfEDN9YjcMqI94TA7w+HgLB3y+ediItu2Scjyr3/B978P0SgMHgwnnSRGVBuRCJSWwnvvwYMPSj9EjIwcKSO53/5WLh1UnAZZjYyUmGjKwmhNZduRI3RKS6N/Izv8E0o0Km4wahScdZZMYExLk8mMjSE9XbbEaCIPPwxz5sDkyTBjRpNP4ylBKuuDRkaesyMcZvGBA64bEcCgNm3YfcEFjPVbx2QoBC+/LEnozz+H886Diy+WTb4WLICuXRMuqU8fST/97W+wdGnCLx8XnAbZoPTZqRl5RCQaJWot3Vu14pOzz3bdiKpjvK6kWSs5n/JyMaAbbpCS+5w5kJcHv/udJG08ZvJkKbrdeWcwS/1BaZB1UDPyAGdoduvnn2OtpV0MidV48JOiIu4rKkrItY7DWnjrLekR++1vYcgQ2LlTIqEXXpCK2NixdeeAPKBdOwJd6g9SWR/UjBJO9RxRXlZWQqOUObt3U5joevXq1XDttWI8Y8fKsOvHP5bcUG4unHKKrwyoJkEt9QdhB9ma+PdTkIQkMlldk3A0SlEolJjkdSgEF14oBrR0qdSYMzIkOvrxj+W+10PFGHFK/cXFUuoPCkHYQbYmakYJ5HuFhZ4YEcgOsmFr3SvrV1TAs8+KyezdKz0I2dmSD1q4EDp0cOe6CSCIpf6gVdJAzSihXNelC495YERwbAfZuM2+tlbyPbt2iQFNnixzf/7xDzjxRKmHB2U+Uww8/LBMIJw82WslsRGkBlkHNSOXiUSjFFTNdxlzwgnc5YEROQzOzm6eGVkrkwg//lhKTP37yzhmxQr4wx9kXtCVV/o6B9RUglbqD1KDrEPyfWp8hJMj+sqqVXx26JCnWq7o3JmVZ59Np6Z8OpcsgUmToKQERo+GZcuk/B6NQseOkuFNQgOqSZBK/UGrpIGakWt8aT2ivn05NTvba0mNY+9emevz4otSAVu8GHJy5Ft4442ydGtAktDxIiil/qA1yDqoGbmAl1Wzuhi0ZAm/Ly6u/6DKShluGSMJkrZtZf7P3XfDRx+B7iYSiFJ/0BpkHdSMXOD13bt9ZUR7wmE+LS8nrWYkY63UrIuKxIAeeQTOPRdeeUX6CN54A844wxvRPqV6qf/RR71WUztBa5B1UDNygW/m5PDhkCG+MCKoVknLzBQDmjsX1q+XRchyc6FbNxmK/eQncNFF8ni8ckBvvy1GN3Vq7c+PGCHDv3A4PtdLAH4v9QexrA9qRnEjEo1yc2EhKw4eBGBE+/YeKzqGY0YDZsyATz6Br3xFesNmzpQkdFaWLEzmRhJ69Ggxu5kzj39u3TppD7nuumCVfZBSfyTiz1J/0BpkHdSM4kAkGmXCmjVM276d/+zf77WcY5SWwqWXUvjZZ6RHo/T+xz/g9NPFgL71LWjTxv0kdGqqLDK9bNmxzRQdHIOaONFdDS7g51J/0BpkHdSMmoljRC9V5Ygm9ezpraBoVBLOfftKhjUlhf4dO/K9Hj1IW7BAzCfRVTDHbKpHR9bCc89Jt/7QoYnVEyf8WuoPYlkf1IyaRU0j8iRHZK10RK5cKSYzY4YsTPa730k+6N13uWHoUJ7y8tM5aJB06c+aJWYJMH++lH0CGBU5+LHUH8QGWQc1o2ZQCZRVVibeiKyVL/PWrRJVdO0q8/4LCqQXbNw4uOYaMIaotRyurEyctrqYOFEmTc6dK7/PnHlsCBdg/FbqD2KDrIOaUROIRKPsC4dplZLCG6efnjgjevdd6QWbO1dWQly9Wu5Ho9C+vZR5aiSh14dCZH3wAS/t2JEYjXXhJKlnzpRv7SuvwGWXSXI7wPit1B/UShqoGTUaZ2j2lVWrOBKNur//WHExjBkjM6Cffhr27ZNhWDQKX/2qtGPUo6GwvBwLnNSqlbs6GyInBy6/HF57TYZrBw4EeohWHT+V+oPYIOugZtQIqueIruvalVZu9WNZC9dfLya0d6/MwencWdaJ7tevUUnouHfrN4eJE+HQIdnNtX17aapNEvxS6g9ig6yDmlGMuJqstlYinvnzxWTefFOGMDffLMty/Pvf8glrAmvLy8lJT29ag2y8GTdOJr8cOCA5LT/vUtJI/FLqD2olDXSropi5d8OG+BqRtbLo2IAB0KuXlGaWL5clOkaNitsExMJQyB9REcgKj43dcihATJ4Mf/2rlPo/+CDxMyicBtkrrkjsdeOFmlGM3NmzJwOzsvhB9+7NO9GcOfKpOXIExo8XQyoqkpxKSoosTBZHJro5nFS+hFPq/8EPpNT/7W8n9vpBbZB10E9pPUSiUf6ybRuV1tKrdeumG1FRkQxRPv8cfvYzaUC95hpJQp97rpTmXTKMm7p353qXdqhVjsfLUn+Qy/qgZlQnzjIgt3z+Oe/t2dO0k4wZA7fdJvNrDh6UHrCVK2Wt6JQU1+P4veEwG0IhKv00PTjJ8bLU73Tra2SURNRcj2hMLDuwWiuVon/+U0xm0SLJ/VxxhcwJev99SHCryOu7dtF38WI2+GE2XgvCq1J/UBtkHdSMatCohdGslSVZDx2SSOfyy+HUU+Gdd2D4cInVL788ceJrsLa8nHRjOFkXRUs4XpT6g9og66BmVIPVhw4xZ/fuuo3IWim9FxTAE0/AOedI5nDTJpg3T2abffWrvlgTujAUol9mJmk+0NLSqF7q/+ijxFwzyGV9UDM6iq3Kq5zZti2Fw4cfb0Rr18JVV8EXX0gV7L334JZbJAl92mnSlOqzL31hebl7+6QpDZLIrv4gN8g6+Ovb4xGRaJRrP/uMp6sG+Cc5w5rKStkZ9Te/gTVrZIfU1FQZlv3mN5CW5ttF6SPRKOv9NMeoBeKU+j/80P2u/qBX0iAGMzLGnGSMKTDGrDHGfGqMuSMRwtxmVmkpvRcuZBTQfsECXty5k/2RCBw+LDtiGAMbN8LZZ8sqiFddJUuzdunitfSYiALPDxzI+IDoTVZuvFEm0btd6g9yg6xDLJFRBLjHWjsQOBf4oTHmVHdlucus0lLyCwvZfOQIFiiPRkk3hm7f+x7k58v6O3PmyMD/scekGhYwMlJS+FaXLgxu08ZrKS2a1FR4/HH3S/1BbpB1aNCMrLXbrbXLq+4fBNYAPdwW5iZTNmyg3Fnkq4qwtUx54AFZnOy002DsWN/lgBrDx2VlzN+372guTPGORJT6g9wg62Aa82E1xvQG5gODrLUHajyXD+QD5OTknPWSX5a+q4VRQG3/agPMTbCWxlJWVkabGKKdR4D/ALNdV1Q3sWr1C27q3batNTfcMJxRo3Zw331rm32+mlpvuOFsevYM8etfr272ud3gkksuWWatHVbvQdbamG5AG2AZcHVDx+bl5Vk/k/vhh5aCguNuuR9+6LW0BikoKIjpuAuXL7cXLl/urpgGiFWrX3Bb709/ai1Yu2RJ889VXWs4bG16upzfrwBLbQO+EdM4xBiTDrwKzLLWvtY8j/Seh/r0IavGECzDGB7q08cjRfFnbXm5VtJ8hlul/qA3yDrEUk0zwDPAGmvtY+5Lcp8JXbsyrX9/clu1wgCZKSkY4NKOHb2WFhf2hMPsDIdl00bFN7hV6k+Gsj7EVk07H7geGGWMWVl1+5rLulxnQteubBoxgrnAimHDqAQe2LjRa1lx4eimjRoZ+Q43Sv1Bb5B1iKWatsBaa6y1Z1hrz6y6vZUIcYmif1YWk3r0YPr27awqK/NaTrMZ3KYNHw4ZwgU+2tVWEdwo9Qe9QdYhuLXrOPNAbi4d0tK4a/36wJfDs1JTGdG+PR2CXOdNYuJd6g96g6yDmlEVHdPTebRvX67u3LnWsn+QeKG0lH8m8fKuyUA8u/qD3iDroGZUjRu6dWNSz56k+LTfLFYe3LyZ6du3ey1DqYd4dfU7DbIaGSUh1lqe2b6daV5vgNVEjjbIaiXN98Sj1J8MPWkOakY1MMYwe+dOflJUxI6KCq/lNJqNhw8TtlYraQEgHqV+NaMk59F+/SiPRvl5AEv9a/20aaPSIM0t9RcWBr9B1kHNqBaCXOpfV/WJVjMKBs0t9a9dG/wGWQc1ozp4IDeXjgEs9d/VsyclI0b4YwdZJSaaU+pPlkoaqBnVScf0dJ7Iy4vvNtYJwBhDj1atvJahNJI//KHxpX5nB9lkqKSBmlG9fLtLF8aecAImQKX+29et4x2dYxQ4+vaVqlpjSv3J0iDroGbUAJXW8rMNG5haUuK1lAbZGw7zv1u3svrQIa+lKE1gypTGlfqTpUHWQc2oAVKNYdWhQ/x840bfl/q1QTbYNLbUnywNsg5qRjHwSN++gSj1a1k/+DSm1J8sDbIOakYxEJRSf2EopDvIBpzGlPqTpUHWQc0oRpxS/4+LiryWUicHIhEGZmXpDrIBJ9ZSfzKV9UHNKGY6pqfz1wEDeLRvX6+l1MkTeXmsGFb/mudKMGio1H/wYFrSNMg6qBk1gis6d+aMqh0Z/DoRMugrDihCQ6X+LVskL6iRUQvmSDTKhM8+49EtW7yW8iU2hkJctmoVi/bv91qKEifqK/UXF8uqDGpGLZhWKSnsj0T41ebNlPqo1L/60CH+3969gV8YTjlGfaX+LVuykqZB1kHNqAk80rcvoWjUVwv4F2pZPympq9S/ZUtW0jTIOqgZNYEB2dn8sHt3X5X6C0MhctLTtUE2yair1F9cnJVUQzRQM2oyv+jdmw5pab6ZCKmbNiYvNUv9kQhs3ZqZVJU0UDNqMh3T03nltNOYlpfntRQAumdkcH67dl7LUFyieql/0yaIRFI0MlKOcUnHjpzYqhXWWiLRqKdaXjztNH7n4zlQSvOoXup3/v7ddBPcdpunsuKKmlEzKYtEOH/FCh4PQFe/EmyclWGcMn80Cn/+c/IYkppRM2mTlkantDQe3LzZs67+WaWlDFyyhC+OHPHk+kozqayEgwflfigEzv/jgQPiOJEIlJUxY0btL582LSEqXSfNawHJwKP9+jHoo494YONGnvJgIL/60CGKQiE6ayUtWJSVQX4+pKRAQQH813/BwoXQqhUMHQozZ8JVV4lRLVpEZeUm4PgZ9pWVCVfuCmpGccDp6p9aUsJtPXocbRlJFGvLy+mXmakNskEjMxPKy+H11+X3xx8/9tz8+fLzmWeOPpRKJZW1fGVTU13UmED00xsnHsjNpUNaGg970CZSqGX9YJKaKmYTyx+Rtm3Jb/d3qGWOfX5+/KV5gZpRnOiYns67gwfzdIJL/c4Osrq6Y0ApLob27es/5sQTYflyntw3gVtvNVWRkCU1FW69FZ58MhFC3UfNKI6c1bYtrVNTCVVWUpGgUv+haJTrunThwoY+0Ir/+Owzqc/ffnvdx9x6K/zqV1LbN4Ynn5R8dkHB+0QiyWNEoGYUd3ZVVDBwyZKELeDfPi2NGQMH8rUTTkjI9ZRmEI1KXf6ss+A734F9+6BfPxg16vihWnY2DBkibvODH0ALWBpGzSjOdM7IYFB2dsJK/aHKSt+uraQgewnt3AmvvSY5oiVLJNq5/XY47zx48UXIyJDIx+GUU2DlymNJ7BaCmpELPNqvX8IW8P/R+vX0W7zY9esojSAchjfflHlCGRkwcSKcey6sWAHnnCNDs3POOXb8iBHw05/K/W99CyZNkogpwVVZr2mwtG+MeRYYB+yw1g5yX1LwqVnqH+zih2pteTnddQdZ74lGpTLWrRts2AB33CGLVO/dCx06yDHdu9f9+gMHYPRoePnlhMj1I7FERjOAMS7rSDqcBfxnfPGFq9cpLC/XSpqXrFghkc327fDrX8Onn8oQzFppInOMqCHuugvmzHFVqt9pMDKy1s43xvROgJakomN6OovPOos+Lm4btCccZmc4TP/MTNeuodTAWpnyfNppMqQ67zyJeDIzYfPm5p27hc+gN7EkP6vMaE59wzRjTD6QD5CTk3PWS7FsiekDysrKaOPy2HwP0AbIiMO5quv9FJgEPAScF4dzx5tEvLfxpF69lZVS/dq0CQYNkuFX+/ZiQh4QtPf2kksuWWatrX/rGmttgzegN7A6lmOtteTl5dmgUFBQ4Or5i0Mh23b+fPvw5s1xOV91vevLy+2UoiK7JRSKy7njjdvvbbz5kt6KCmvffdfaffusBWvz861dv97ajz7yTF91gvbeAkttA76hvWkuc1Lr1lzUvj0Pbt7Md088kS4Z8YiPhL6Zmfy6T5+4nU8BZsyA3r1h7lx48EHJBZWWyjYdiqtoaT8BuFXqX1dezv5IJK7nbJEsXCiVrEhEVsAvKoJf/lLyQyeeqEaUIBo0I2PMC8BCoL8xpsQY8333ZSUXTqk/3gv4X7l6NTesXRu387UYrJVlOfr3h6lTpRSfmSmzoK2F738/tuZVJa40+I5ba6+11naz1qZba3taa59p6DXK8Til/nf27InL+bRBtpFEo3DoEDz2mBhNeTl87Wtw2WUwYYIs46EG5CmaM0oQHdPTKTznHE6IU/l24+HDhK3Vsn59VFTA8uXQqxf06AEPPADXXCPDsq5d4Y9/9FqhUg01owTiGNHqsjJOycqiVTP+EjubNmpkVINIBF54AQYOhKeeklnRBw/KHKBevbxWp9SDxqUJZs2hQwxeurTZXf1rdQfZL/Puu9IJv3UrfPe7Yj5/+YvkgNq0USMKABoZJZiB2dlc3qnT0VJ/1yaW+sedcAKd0tPp2JJn7e7cCRdfDFOmwJ49sH+/zIbWVQwCiUZGHvBI376EolEeaEapf0B2Nt/r1i2OqgJANAqHD8N998n6PtGodMOfe670g735ZotvqQgyakYeMCA7mx92796sUv/ru3ax5fDhOCvzIRUV8MknsGaNrAc0bZrs9fzBB5KEfvbZL68FpAQWNSOP+EXv3nTLyGBlE8xoTzjMN1av5sUdO1xQ5gPCYUlCr1kD48bBGWdAnz6yJMePfgTDh8MFF3itUokzmjPyiI7p6RSde26TKmpJW0mbPRsWLYJvfxuuuw7efluW1XDyagne7EBJLBoZeUirlBSstfxrzx6ONGIB/8JkqqQVF0vk8/bbsHQprF8vaz9bC2PGHDMiJelRM/KYpQcPMubjj/lTI0r9a8vLSTeGk11cK8k1olEZhn33u7IqYmUlnHkmnHoqPPQQvPpqi1h8XjkeNSOPObtdO8ZWlfpjXcC/MBQK1g6yFRXS/7VwoSShX3pJGlJffBFOPlm2cc7N9Vql4jEB+TQnN43t6n+8Xz9mDhjgsqpmEg7LAmSbN0tD6uDBcPrpslfYhAlwySVw0UVNO/fbb0v0NHVq7c+PGAE5OaJBCQxqRj6gsV39ua1bM6xduwQoawKzZsme8XPnSjRUXCwGdPCgzIQeOLD51xg9WoZ4M2ce/9y6dZIEv+46nXMUMNSMfMIDubkMzMpi25Ej9R63B/ifkhJK/DTHaN06STovXgxvvQUffwxf/apsVnjhhfFfmjU1VaKrZcvE6KrjGNTEifG9puI6akY+oWN6Op+cfTaXN7AzbCFw5/r1lDRgWq4SjcrtsstkuFVeDgMGQM+eEhk9+6z7GhyzqR4dWQvPPSdrVA8d6r4GJa6oGfkIYwzhaJRntm+vs9RfXPUz4WX9igpZgvWddyQyefdduPlm2Z5n8GCZpNijR+L0DBok0disWWKMIDuwbtqkUVFAUTPyGf/Zv5+bCgvrLPVvAXIS1SAbDstExB07oFUrGXoNGybDsDFjZKue8893X0ddTJwIJSWSnwKJkpwhnBI41Ix8xsiOHest9W8hATOvp0+H55+X0vvVV8O2bbLj6ccfQ+fOUhXzA06SeuZMCIXglVdk6NjSGoiTBDUjH1JfqX8LLg3RVq+Gs8+W/q9nnoFVqyTCsFYmJbZtG/9rNpecHLj8cnjtNRmuHTigQ7QAo2bkQ+or9T8P/Pbkk5t/kWhUjGbwYLjpJti9W5pRO3aUyYm//30wZkJPnChrW99zj2yqeOWVXitSmog2yvqUB3JzWVVWRkWNRHZroHNT+7UiEdkV9d//hvHj4aOP4JZbpAQ/fLgsVBY0xo2DTp1kcbWbbvJsh1el+agZ+ZSO6enMPfPMLz327717mQYMi0Rokxbjf104LBWwiy+WyOHrX4cnnpCF6ocMkYR0kMnIkKhOCTxqRj5nXzjMn7Zu5d5evXhvzx5eA2Y11JMWjcpcn+7dJQd0993SDb97t0QRIHOCFMVHaM7I53x08CAPbNrE1JISCkMhekDdDbLLl0upvbQUfvYzmZ18552SG+rb95gRKYoP0cjI51zWqRNjO3Xi/g0bqKx6LG3ePPK7d+fJU06RYdigQVLmHjpUtmPOzIQvvvBUt6I0Fo2MAkDblJSjRgRQCfx561Zuu/NO2Zrn+uvhqqskH/Tqq9ChgzdCFaUZqBkFgJd37Tr+QWOYdtVVsh7Qz38uJXpFCTBqRgGgspGPK0oQUTMKAKmNfFxRgoiaUQDI7969UY8rShDRaloAeLJqi55p27ZRiURE+d27H31cUZIBjYwCwpN5eURGjqQAiIwcqUakJB1qRoqi+AI1I0VRfIGakaIoviAmMzLGjDHGFBpj1htj7nNblKIoLY8GzcgYkwo8AVwOnApca4w51W1hiqK0LGKJjIYD6621G6y1FcDfAV1OT1GUuBLLPKMeyNLLDiXAOTUPMsbkA/lVvx4xxqxuvryE0BmopfnLtwRJb5C0QrD0BkkrQP+GDojFjGpbCNke94C104BpAMaYpdbaQCwhGCStECy9QdIKwdIbJK0gehs6JpZhWglwUrXfewLbmipKURSlNmIxo4+AU4wxJxtjMoDxwBvuylIUpaXR4DDNWhsxxkwC/oW0RT1rrf20gZdNi4e4BBEkrRAsvUHSCsHSGyStEINeY+1x6R9FUZSEozOwFUXxBWpGiqL4griaUZDaRowxzxpjdgRhPpQx5iRjTIExZo0x5lNjzB1ea6oPY0xrY8wSY8yqKr3/7bWmhjDGpBpjVhhj5nitpSGMMZuMMZ8YY1bGUjL3EmNMB2PMK8aYtVWf3xF1HhuvnFFV28jnwGXIdICPgGuttZ/F5QJxxhhzEVAGzLTWDvJaT30YY7oB3ay1y40xbYFlwDd8/N4aINtaW2aMSQcWAHdYaxd5LK1OjDF3A8OAdtbacV7rqQ9jzCZgmLXW95MejTF/Az6w1k6vqsZnWWv31XZsPCOjQLWNWGvnA3u81hEL1trt1trlVfcPAmuQmfG+xAplVb+mV918WykxxvQExgLTvdaSTBhj2gEXAc8AWGsr6jIiiK8Z1dY24tsvTFAxxvQGhgCLPZZSL1XDnpXADuA9a62f9T4O3AtEPdYRKxZ41xizrKoNy6/0AXYCf60aAk83xmTXdXA8zSimthGl6Rhj2gCvAndaaw94rac+rLWV1tozkRn7w40xvhwKG2PGATustcu81tIIzrfWDkVW0vhhVcrBj6QBQ4E/W2uHAIeAOnPJ8TQjbRtxkarcy6vALGvta17riZWqsHweMMZbJXVyPvD1qjzM34FRxpjnvJVUP9babVU/dwCzkRSJHykBSqpFxa8g5lQr8TQjbRtxiaqE8DPAGmvtY17raQhjTI4xpkPV/UzgUmCtp6LqwFp7v7W2p7W2N/KZnWut/Y7HsurEGJNdVcSgasgzGvBlRdha+wWwxRjjdOx/Baiz6BK3rYqa2DbiGcaYF4CRQGdjTAnwC2vtM96qqpPzgeuBT6ryMACTrbVveSepXroBf6uqsKYAL1lrfV8yDwhdgdny94k04Hlr7TveSqqX24FZVQHKBuDGug7UdhBFUXyBzsBWFMUXqBkpiuIL1IwURfEFakaKovgCNSNFUXyBmpGiKL5AzUhRFF/w/wH2b+xBRPT3nAAAAABJRU5ErkJggg==\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "t1 = np.array([2, 0.25])\n", "t2 = np.array([2.5, 3.5])\n", "t3 = np.array([1, 2])\n", "\n", "x_coords, y_coords = zip(t1, t2, t3, t1)\n", "plt.plot(x_coords, y_coords, \"c--\", x_coords, y_coords, \"co\")\n", "\n", "plot_vector2d(v, t1, color=\"r\", linestyle=\":\")\n", "plot_vector2d(v, t2, color=\"r\", linestyle=\":\")\n", "plot_vector2d(v, t3, color=\"r\", linestyle=\":\")\n", "\n", "t1b = t1 + v\n", "t2b = t2 + v\n", "t3b = t3 + v\n", "\n", "x_coords_b, y_coords_b = zip(t1b, t2b, t3b, t1b)\n", "plt.plot(x_coords_b, y_coords_b, \"b-\", x_coords_b, y_coords_b, \"bo\")\n", "\n", "plt.text(4, 4.2, \"v\", color=\"r\", fontsize=18)\n", "plt.text(3, 2.3, \"v\", color=\"r\", fontsize=18)\n", "plt.text(3.5, 0.4, \"v\", color=\"r\", fontsize=18)\n", "\n", "plt.axis([0, 6, 0, 5])\n", "plt.gca().set_aspect(\"equal\")\n", "plt.grid()\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Finally, subtracting a vector is like adding the opposite vector." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Multiplication by a scalar\n", "Vectors can be multiplied by scalars. All elements in the vector are multiplied by that number, for example:" ] }, { "cell_type": "code", "execution_count": 19, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "1.5 * [2 5] =\n" ] }, { "data": { "text/plain": [ "array([3. , 7.5])" ] }, "execution_count": 19, "metadata": {}, "output_type": "execute_result" } ], "source": [ "print(\"1.5 *\", u, \"=\")\n", "\n", "1.5 * u" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Graphically, scalar multiplication results in changing the scale of a figure, hence the name *scalar*. The distance from the origin (the point at coordinates equal to zero) is also multiplied by the scalar. For example, let's scale up by a factor of `k = 2.5`:" ] }, { "cell_type": "code", "execution_count": 20, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "k = 2.5\n", "t1c = k * t1\n", "t2c = k * t2\n", "t3c = k * t3\n", "\n", "plt.plot(x_coords, y_coords, \"c--\", x_coords, y_coords, \"co\")\n", "\n", "plot_vector2d(t1, color=\"r\")\n", "plot_vector2d(t2, color=\"r\")\n", "plot_vector2d(t3, color=\"r\")\n", "\n", "x_coords_c, y_coords_c = zip(t1c, t2c, t3c, t1c)\n", "plt.plot(x_coords_c, y_coords_c, \"b-\", x_coords_c, y_coords_c, \"bo\")\n", "\n", "plot_vector2d(k * t1, color=\"b\", linestyle=\":\")\n", "plot_vector2d(k * t2, color=\"b\", linestyle=\":\")\n", "plot_vector2d(k * t3, color=\"b\", linestyle=\":\")\n", "\n", "plt.axis([0, 9, 0, 9])\n", "plt.gca().set_aspect(\"equal\")\n", "plt.grid()\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "As you might guess, dividing a vector by a scalar is equivalent to multiplying by its multiplicative inverse (reciprocal):\n", "\n", "$\\dfrac{\\textbf{u}}{\\lambda} = \\dfrac{1}{\\lambda} \\times \\textbf{u}$" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Scalar multiplication is **commutative**: $\\lambda \\times \\textbf{u} = \\textbf{u} \\times \\lambda$.\n", "\n", "It is also **associative**: $\\lambda_1 \\times (\\lambda_2 \\times \\textbf{u}) = (\\lambda_1 \\times \\lambda_2) \\times \\textbf{u}$.\n", "\n", "Finally, it is **distributive** over addition of vectors: $\\lambda \\times (\\textbf{u} + \\textbf{v}) = \\lambda \\times \\textbf{u} + \\lambda \\times \\textbf{v}$." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Zero, unit and normalized vectors\n", "* A **zero-vector** is a vector full of 0s.\n", "* A **unit vector** is a vector with a norm equal to 1.\n", "* The **normalized vector** of a non-null vector $\\textbf{v}$, noted $\\hat{\\textbf{v}}$, is the unit vector that points in the same direction as $\\textbf{v}$. It is equal to: $\\hat{\\textbf{v}} = \\dfrac{\\textbf{v}}{\\left \\Vert \\textbf{v} \\right \\|}$\n", "\n" ] }, { "cell_type": "code", "execution_count": 21, "metadata": {}, "outputs": [ { "data": { "image/png": "iVBORw0KGgoAAAANSUhEUgAAAVQAAAD4CAYAAACzOx6UAAAAOXRFWHRTb2Z0d2FyZQBNYXRwbG90bGliIHZlcnNpb24zLjUuMiwgaHR0cHM6Ly9tYXRwbG90bGliLm9yZy8qNh9FAAAACXBIWXMAAAsTAAALEwEAmpwYAAAcSklEQVR4nO3deXxV9Z3/8dfn5mYjwbCFAAIqixZFEIMLY/0V+qBKbUcfOtVW2k4dy+BYndrWhS6Pjq22Y522th2rHdfaxZHqFKqtOggKo7ZaJRRBRIuiIksJsich2z3f3x8nyGJCEvK999xz8n4+HnlkuZfvfRPIO99zzvecY845RESk51JRBxARSQoVqoiIJypUERFPVKgiIp6oUEVEPElH8aKDBg1yRx99tPdx6+vrKSsr8z5uNsQpK8Qrb5yyQrzyxikrZCdvTU3Nu865ynYfdM7l/K26utplw+LFi7MybjbEKatz8cobp6zOxStvnLI6l528wFLXQbdpk19ExBMVqoiIJypUERFPVKgiIp6oUEVEPFGhioh4okIVEfFEhSoi4okKVUTEExWqiIgnKlQREU9UqCIinqhQRUQ8UaGKiHiiQhUR8USFKiLiiQpVRMSTHheqmZWY2Qtm9pKZrTKzb/sIJiISNz7uKdUEfNg5V2dmhcCzZva4c+55D2OLiMRGjwu17R4rdW2fFra9uZ6OKyISNxb2YQ8HMSsAaoAxwG3OuTntPGc2MBugqqqqeu7cuT1+3YPV1dVRXl7ufdxsiFNWiFfeOGWFeOWNU1bITt5p06bVOOcmt/tgR3fvO5w3oB+wGBh/qOfprqfxyupcvPLGKatz8cobp6zOxfyup865HcASYIbPcUVE4sDHUf5KM+vX9nEpMB14tafjiojEjY+j/EOBX7TtR00BDzrn/uBhXBGRWPFxlH8FMMlDFhGRWNOZUiIinqhQRUQ8UaGKiHiiQhUR8USFKiLiiQpVRMQTFaqIiCcqVBERT1SoIiKeqFBFRDxRoYqIeKJCFRHxRIUqIuKJClVExBMVqoiIJypUERFPVKgiIp6oUEVEPFGhioh4okIVEfFEhSoi4okKVUTEExWqiIgnKlQREU9UqCIinqhQRUQ8UaGKiHiiQhUR8USFKiLiiQpVRMQTFaqIiCcqVBERT1SoIiKeqFBFRDzpcaGa2QgzW2xmq81slZld5SOYiEjcpD2M0Qpc7ZxbZmZ9gRozW+ice8XD2CIisdHjGapzbpNzblnbx7uB1cCRPR1XRCRuvO5DNbOjgUnAn32OKyISB+ac8zOQWTnwf8B3nXPz2nl8NjAboKqqqnru3LleXnd/dXV1lJeXex83G+KUFeKVN05ZIV5545QVspN32rRpNc65ye0+6Jzr8RtQCCwAvtKV51dXV7tsWLx4cVbGzYY4ZXUuXnnjlNW5eOWNU1bnspMXWOo66DYfR/kNuAdY7Zy7pafjiYjElY99qGcAnwU+bGbL297O8TCuiEis9HjZlHPuWcA8ZBERiTWdKSUi4okKVUTEExWqiIgnKlQREU9UqCIinqhQRUQ8UaGKiHiiQhUR8USFKiLiiQpVRMQTFaqIiCcqVBERT1SoIiKeqFBFRDxRoYqIeKJCFRHxRIUqIuKJClVExBMVqoiIJypUERFPVKgiIp6oUEVEPFGhioh4okIVEfFEhSoi4okKVUTEExWqiIgnKlQREU9UqCIinqhQRUQ8UaGKiHiiQhUR8USFKiLiiQpVRMQTFaqIiCdeCtXM7jWzWjN72cd4IiJx5GuGeh8ww9NYIiKxlPYxiHPuaTM72sdYSdOQybCxqYlNzc1sbG5mV2srLc5R2dLCHRs3UppKMaSoiKFFRQwrLmZAOo2ZRR1bDtOzz0JZGUyaBPfeC5/8JGzfDi++COefD089BVVVcMIJ8LOfwUc/GnVi8cmcc34GCgv1D8658R08PhuYDVBVVVU9d+5cL6+7v7q6OsrLy72P21UtzlGfyVCfybA7k2FPEBAQbgYYsP93elgmw8aCAmh7DCBoe19kRnlBAeUFBfQpKKBPKvpd3VF/b7sjiqxPPDGYW28dSyZjmEE67WhsTFFcHBAE0NoaftzSsu/xlhbjuON2c+ONf9T3NkuykXfatGk1zrnJ7T3mZYbaFc65O4E7ASZPnuymTp3q/TWWLFlCNsbtSOAcL+7ezbwtW/hNbS2bW1ooSqepy2TeK8eO/KCujms6+Yfuk0pRYIYDZgwYwKcGD+as/v3pm87ZP9t7cv297Ykosk6YAG+8AQ8+eODXm5sL3vu4qWnfx5MnwxNPQEVFf55+ulzf2yzJdd7c/2QmwDuNjfx0wwbu3LSJjHPsyWRobXus0ePrNAT7avl/tmxhwbZtNAUB0/v359oRI/hQv37aPZAnBgyAKVPeX6gHS6fh2mvhlFOgf//cZJPcUaF2kXOOp3bs4Hvr1vHMjh04oNnT7pKu2p3JAPD4tm08vXMnA9Jprh0xgn8aOpSygoJO/rRkW0EB9OkDDQ3tP96/P1x8Mfz7v+c2l+SOr2VTDwDPAceZ2Xoz+7yPcfPFczt3MrmmhvNWrmTR9u00OZfzMt2fA+oyGdY1NTFn7VqG/+lP3LZ+PS1BZzsa8tOll4IZbNny/sdefx2KiuDyy3Ofqys2b4adO2HaNPjiF+G889p/3tlnw/LlcMstOY0nOealUJ1zFzvnhjrnCp1zw51z9/gYN2qv1tfzkZdeYvpLL7Gsro76PCyshiBgRybDnLVrGfn888zdvBlfBxpzZcKE8P3L7axinjMHSkrg29/ObaZDWbMGFi6EJ5+EIUPCI/d33QXvvgsHHz8sLAyP7l93HYwcCcXF0WSW3NAmfztag4Cb1q3jpnXraGo7Up/v6oOA+uZmZr32Grdv3Mh/jxvH8JKSqGN1yf6FOm3avq//6U8wb164iTx4cDTZ9tq6FW66Cf7xH8MZdXMzLFsGjY0HluQ//zM8/DDU1UF5Ofz0p/C5z0WXW3JLhXqQVfX1XLRqFW83NrInD2eknakPAp7btYtxL7zAj8eO5dIhQ/L+wNXEieH7g2eo11wDI0bAl7+c+0x7ff3r4TrSz3wG7r8/LMelS/c9fvCCiw99CE49NSzTa68NP5beI/oFjnnkjo0bOaWmhtUNDXm5ed9Vrc5RFwRctWYNM1asYHdra+d/KEIDB8LQobBq1b6vPfggPPdcOCvM5UQ7k4GamnCf7sKF4exzzBg44wzYtAlOPLHzMUaOhB/8AD74wXD/r/QemqECLUHAFWvWcP/mzbGclXakPgh4escOJi5dyqKJExlVWhp1pA5NmAB//nP4cXMzfO1r4dKimTOz/9pbtoQzyuOPhyAI943+5CfhMqiPfKT74/385/4zSjz0+kLd2tLCx1asYGV9/QHrPpOi0Tnebmxk0tKl/G78eKbl6eLHCRNgwQJYvx4eegjWroX77gtnitnw2mvh0fm33gpPD33ySZg/P9zFMHBgeMRepLt6daFuampiyrJlbGpujnQZVLYFwK5Mho+tXMn948ZxfmVl1JHeZ++BqWeege98By64AM480+9r1NaGy5b+5V/g5JPD/Z3z5r3/wJLI4eq1hbqhqYnTamrY3NJCa4LLdH97goBPr17Nz4OAT1ZVRR3nAHsL9Utfgt274eab/Y19xRVw5JEwfjzcc094JL6uLnuzX+m9euVBqc3NzUxZtiwZZbpuXbhtvG5dl56+Jwj4p9de4+F3381urm4aNy48gFNbGxbgmDGHP5Zz8PTTYWH+5S/hPtnKSjj33HB/6ejRKlPJjl43Q92TyTB1+XI2NTWR38e+u8A5+P73wx2Oy5aFR1K60BR7goCLX3mFpyZO5PSKihwE7VxhITQ1Hf6f37oVKirCUz9PPHEC99wDP/whHHtsuOheJBd61QzVOcfMV17h7cbG+JcpwGOPwd/+FjbGpk3hUZ0u2hMEnLNyJesbfV7OJbfWrAmXWt15JwwaBCtXhgeXrr/+FU46Cb7ylfDapCK50qsK9Ttvv80T27cnY2nUzp1hkc6ZA8OGhec23nEH7NrV5SF2ZzJ8ZMUK9rRddCUONm+Gb34z3DVw7LHhpHzmTNizJ7yo85lnwhFHJOLXpcRQr9nkX7RtGzetW5eMMoVw+/Z3v9v3+SmnhOt+uqG1bUnVpa++ygMnnOA3n0etreHFUU49Nbyi0+23h58HgfaFSn7pFTPUXa2tXLx6dXLK1KM9QcAjW7fy6NatUUc5gHPhHoziYtiwIXyrqAjPo9+6NZyUq0wl3/SKQr1yzRrq8vz0yyg1BAGfXb2a7S0tkebYtStcE2oWLm0qK4MbbwwvjPLYY3DRRZHGE+lU4gt14bZt/HbLFhrjvjxqfzffHF6WaceO9z+2YUN4vuSPftStIRsyGS7761/95OuGN98Mbx1y883hDHTTJvj97/edC3/ddZDHZ8yKHCDRhdoSBFzy6qvJO6V09Ojw/Ztvvv+xO+4IF3Reckm3hmxyjke3buWPO3f2PF8nNmwIC3TzZhg1Cn71q32L7Y85Bj7+cejXL+sxRLxLdKHes2kTO5O4qT9qVPj+4EJ9+eXw3M2ZMw/rhkUNQcCVa9Zk5QLVe/aEp3w+9BD8+tfh6aXFxeEBp299K7wnk5Y4SdwltlAbMhm+/uabsb4MX4c6mqH+13+FOxwvvPCwh17T0MBj27b1INyBHnoojLRrFzz/fLhZP2dOeHppv37hUXuRpEhsof54/XqaklimELbSwIHhpZL2Wrw4XOU+a1aPLsJZHwT865o1BIc5S21oCI/Cm8H114ezzquuCifMy5fDWWcddjSRvJfIQm0JAr7/zjvJ23e6v1Gj9hVqSwvcfTd84AMwfXqPh97S0sKT27d3+fnvvBPuF73mmrBAnQs366++Gs45B77xDV1oWXqHRBbqI1u3kknSUf32jBoVHsXZsiVc4L9xY7ja3cPizLpMhv94551DPuett8ITtdauDa9QP29eWKi7doWngX7603DEET2OIhIriTxT6uZ16967h31i7d2PumJFOB0888x918Dz4NmdO3mnsZER+91/ZPfu8B5Lf//38PjjcO+9YZ83N4cXNxHp7RI3Q321vp6X6+ujjpF9e4/033ZbuOPyssu8Dh84x20bNgDhSqxZs6rZsQMefTTcrP/Rj8LLCRQVqUxF9krcDPU3tbXJ39wHOOqosMm2b4dPfCK8gnJH5s8PLxDaVUEhzS0DuXn144z4aXj868wz32XYsL6sXdvz6CJJlbhCnVtbm+jbmbwnnYYnnujac1euDA+xH9IQoBm4FZgJNoiCGfP5uwvPZtLgPgwZ8jYFBcf0KLJI0iVqk7/FOd6M8fU9s2bGjPDKy+8zCjgfqAY2AedA+pswcAzcdTOFXxvIk435dWV/kXyWqELd2dpKWpcger+TTw6vdQdAP+AW4FTg+8B/AjVAMZT8D5w+DH75nzB6NI1BwP21tdFkFomhRBXqrkwmmWdG9dT69dD4JWAecCRwIdAK/AMwInxOscEXvgA33HDAbHZVfT3N+p6KdEmi9qHWJ32pVHe88TbcMBfWPU5YoJWQ+gsEq3ivRCE8sFVRAd/73r6lWPspSaVY1RtWTYh4kJgZan0mQ0tvOBh1KCv+Bp//Ekwrhlmfg3Ur4Lhb4YFLYOEFUPT9A59fUhJeBv8Xv2i3TAEyzlGze3fWo4skQWJmqMvr6pLz26E7nt8Gt86HjZuBJ4D7YcodcPl2GHH/gc+dMiU85x/CSz1dfnm4Sv8Q+50bgoA/7txJD+7qLNJrJKZQX21ooNfMT1dugn+rhx0/BB4Cvggf/iZc/nsYdHXHf+7ss8P1qP37w003wZiu1eTyujo+5yW4SLIlplA3NDWR6MtpvvUWfLkFdjQQHlx6EE5/Hr76RrgPlK92PkZ1dXgJ/A9+sINlVO3bHPGtUUTiIjGF+uaePYyPOoRva9+C6x+B9fOAqcB0OHYA/MdXoGI18JnujZdOH9b187apUEW6xEuhmtkM4CdAAXC3c+57PsbtjrebmpJRqCs3wU++C28sAIYC34Wxt8MN18CQ8kgiZQAtnBLpXI8L1cwKgNuAjwDrgRfN7BHn3Cs9Hbs7apubc/lyh2/RIrj7bq6prQ0vZT9rFpSdDD/7JbxTDPwGuB1OuRH+9VwYcVfUiSk2o1VrUUU65WOGeirwunNuLYCZzQXOA3JaqLFYMrVoUXg7z6YmYDBsvgq+ezvwbcBg6l3whd9D5Y0RBz1Qyiwr95kSSRofK42OBPa/GvH6tq/lVGscfuDvvrutTAGmALOAQhg0FBb3h+uvg8q+EQbsWAy+uyKR8zFDbW8R4/t+/sxsNjAboKqqiiVLlnh46X2+XF9PZSbDD+rqvI7r0zUHnBf/cNsbsNXyOncKaHbO+79ZttTV1cUmK8Qrb5yyQu7z+ijU9RxwLiPDgY0HP8k5dydwJ8DkyZPd1KlTPbz0Ple88AKX1tZyTXk0B266ZPDg8Gb07Xw9n3OXpVL8NpPB979ZtixZsiQ2WSFeeeOUFXKf18cm/4vAWDM7xsyKgE8Bj3gYt1sGxuGy8bNmhWco7a+4OPx6Hmt2TlfxEumCHs9QnXOtZnYlsIBw2dS9zrlVPU7WTSMPLqp8tPeOpHffDfsf5fdwp9JsK4g6gEgMeFmH6px7DHjMx1iHa3RpaZQv33XTp8P06fygri6vN/P31z+dDm9VLSKHlJjriQwrLk7OXybPDC4qijqCSCwkpoPGlpa2u9xAeu6Ebpz3L9KbJaZQTy4v1+mRWVBqxpn9+kUdQyQWElOo/QoLdSQ6CwpTKapjsq9XJGqJKVSAPqlE/XXyQkMQMFGFKtIliWqgI9JpSlWqXo0qKaG0QIumRLoiUe3TL52Yy7vmhSIzPjV4cNQxRGIjUYVaZEZlHM6YiolCM84fNCjqGCKxkahCBbho8ODk3IYgYsWplPafinRD4gr1k5WVFGs/ao+lgYsqKzGtnBDpssQ1T3XfvhwZh/P681xhKsUXhw+POoZIrCSuUM2MOSNHUq5Zao+cUFbGuLJE30dWxLtEts6nBg/WFeZ7oG9BAXNGjOj8iSJygEQWap+CAi4bNowSzVIPS0kqxXk6ui/SbYltnG8cdZSu4XkYylIpfjh6NIX6ZSTSbYn9qRlQWMickSN1Omo3VRYVMbOqKuoYIrGU6La5esQIilSoXVaWSnHrmDEUaKmUyGFJdNv0KSjg1jFjKFOpdiptxqS+ffnYwIFRRxGJrcQ3zaerqphyxBHohNRDKzbjgXHjtJBfpAcSX6hmxi/HjaNEV0zqUFkqxY/HjGF4SUnUUURiLfGFCjC0uJifjR2rA1TtKDKjum9fPj90aNRRRGKv1zTMp4cMYWZVlUp1PwYMSKeZN368NvVFPOhV7XL72LGMLyujSOUBhHc4WHTSSQzUJQ9FvOhVhVqYSvHYhAkMSKd7/R1SS1Mp/vv44zlB5+uLeNOrChVgYGEhSyZNoqIXX92/TyrFTcccw7k6vVTEq15XqADH9enDMyedREVBQa+bqfZJpfjmUUdxlS5+IuJdryxUgPHl5fzx5JPpl073mm9Cn1SKG445hq8edVTUUUQSqbd0SbtOKCvjxepqhhcXU5zwA1WlqRS3jR3L1ZqZimRNry5UgNGlpaw45RT+rqIikUuq0mb0T6d5auJELtFaU5GsSl6DHIaKdJqFEydy2bBhiSrVPqkUY0pLWTF5MqdXVEQdRyTxktMePVRgxi1jxjB//HgGFRbG/uLUpakUVx55JMsnT9YppSI5Eu/WyIKzBgzg9dNO4xODBsVyttonleKYkhKemTSJm0eP1h1gRXJIP23tqEin+dXxx/Pw+PGMLimJxeX/is0oS6WYM3Ikq089leq+faOOJNLr9N7V7V0wfcAA/nraacytreUrr79OXSZDfRBEHesAhWakzfj80KF86+ijdRqpSIRUqJ1ImTGzqopPVFZy39/+xk3r1rGluZmGIIj0zqrlqRQOuGTIEOaMHMkI7ScViVyPtmXN7EIzW2VmgZlN9hUqHxWlUsweNoy1p53GgokTOXfgQIrN6JvD66wWm9EnlWJsaSk/GTuW2jPO4KfHHqsyFckTPZ2hvgxcANzhIUssmBlnVFRwxoknsr2lhf/dto0Hamt5cvt20mY0BgHNzs/cNQWUFxTQGAR8oE8fZlZVcd7AgXxAFzQRyUs9KlTn3Gqg115Ls39hIRdXVXFxVRUtQcCfdu3ihV27+L8dO6jZvZutra2UpFKkgFbnaAwCMu2MU5pKUdj2PWxxjhThWVz/r6KC0444gqn9+jGoqCiXfzUROQzmPMymzGwJcI1zbukhnjMbmA1QVVVVPXfu3B6/7sHq6uooLy/3Pu7hCoDmthlri3O0BAEZ5wiAsqYmGoqLSZlRaEaRGYVtxVqYh7+g8u17eyhxygrxyhunrJCdvNOmTatxzrW/i9M5d8g3YBHhpv3Bb+ft95wlwOTOxtr7Vl1d7bJh8eLFWRk3G+KU1bl45Y1TVufilTdOWZ3LTl5gqeug2zrd5HfOTffR6iIiSZf/K9ZFRGKip8umzjez9cAU4FEzW+AnlohI/PT0KP98YL6nLCIisaZNfhERT1SoIiKeqFBFRDxRoYqIeKJCFRHxRIUqIuKJClVExBMVqoiIJypUERFPVKgiIp6oUEVEPFGhioh4okIVEfFEhSoi4okKVUTEExWqiIgnXu562u0XNdsCvJ2FoQcB72Zh3GyIU1aIV944ZYV45Y1TVshO3qOcc5XtPRBJoWaLmS11Hd3eNc/EKSvEK2+cskK88sYpK+Q+rzb5RUQ8UaGKiHiStEK9M+oA3RCnrBCvvHHKCvHKG6eskOO8idqHKiISpaTNUEVEIqNCFRHxJFGFamYXmtkqMwvMLG+XdpjZDDN7zcxeN7OvRp3nUMzsXjOrNbOXo87SGTMbYWaLzWx12/+Dq6LO1BEzKzGzF8zspbas3446U2fMrMDM/mJmf4g6S2fM7C0zW2lmy81saa5eN1GFCrwMXAA8HXWQjphZAXAb8FHgeOBiMzs+2lSHdB8wI+oQXdQKXO2cGwecDlyRx9/bJuDDzrmJwEnADDM7PdpInboKWB11iG6Y5pw7SetQD5NzbrVz7rWoc3TiVOB159xa51wzMBc4L+JMHXLOPQ1sizpHVzjnNjnnlrV9vJvwh//IaFO1z4Xq2j4tbHvL2yPEZjYc+Bhwd9RZ8lmiCjUmjgTe2e/z9eTpD32cmdnRwCTgzxFH6VDbJvRyoBZY6JzL26zAj4HrgCDiHF3lgCfMrMbMZufqRdO5eiFfzGwRMKSdh77hnHs413kOg7XztbydmcSRmZUDvwW+5JzbFXWejjjnMsBJZtYPmG9m451zebev2sw+DtQ652rMbGrEcbrqDOfcRjMbDCw0s1fbtrayKnaF6pybHnWGHloPjNjv8+HAxoiyJI6ZFRKW6f3OuXlR5+kK59wOM1tCuK867woVOAM418zOAUqAI8zs1865z0Scq0POuY1t72vNbD7hrrasF6o2+XPvRWCsmR1jZkXAp4BHIs6UCGZmwD3AaufcLVHnORQzq2ybmWJmpcB04NVIQ3XAOfc159xw59zRhP9fn8rnMjWzMjPru/dj4Cxy9IsqUYVqZueb2XpgCvComS2IOtPBnHOtwJXAAsKDJg8651ZFm6pjZvYA8BxwnJmtN7PPR53pEM4APgt8uG25zPK2WVU+GgosNrMVhL9kFzrn8n45UkxUAc+a2UvAC8Cjzrn/zcUL69RTERFPEjVDFRGJkgpVRMQTFaqIiCcqVBERT1SoIiKeqFBFRDxRoYqIePL/AR/rja2S8NzeAAAAAElFTkSuQmCC\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "plt.gca().add_artist(plt.Circle((0, 0), 1, color='c'))\n", "plt.plot(0, 0, \"ko\")\n", "plot_vector2d(v / LA.norm(v), color=\"k\", zorder=10)\n", "plot_vector2d(v, color=\"b\", linestyle=\":\", zorder=15)\n", "plt.text(0.3, 0.3, r\"$\\hat{v}$\", color=\"k\", fontsize=18)\n", "plt.text(1.5, 0.7, \"$v$\", color=\"b\", fontsize=18)\n", "plt.axis([-1.5, 5.5, -1.5, 3.5])\n", "plt.gca().set_aspect(\"equal\")\n", "plt.grid()\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Dot product\n", "### Definition\n", "The dot product (also called *scalar product* or *inner product* in the context of the Euclidian space) of two vectors $\\textbf{u}$ and $\\textbf{v}$ is a useful operation that comes up fairly often in linear algebra. It is noted $\\textbf{u} \\cdot \\textbf{v}$, or sometimes $⟨\\textbf{u}|\\textbf{v}⟩$ or $(\\textbf{u}|\\textbf{v})$, and it is defined as:\n", "\n", "$\\textbf{u} \\cdot \\textbf{v} = \\left \\Vert \\textbf{u} \\right \\| \\times \\left \\Vert \\textbf{v} \\right \\| \\times cos(\\theta)$\n", "\n", "where $\\theta$ is the angle between $\\textbf{u}$ and $\\textbf{v}$.\n", "\n", "Another way to calculate the dot product is:\n", "\n", "$\\textbf{u} \\cdot \\textbf{v} = \\sum_i{\\textbf{u}_i \\times \\textbf{v}_i}$\n", "\n", "### In python\n", "The dot product is pretty simple to implement:" ] }, { "cell_type": "code", "execution_count": 22, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "11" ] }, "execution_count": 22, "metadata": {}, "output_type": "execute_result" } ], "source": [ "def dot_product(v1, v2):\n", " return sum(v1i * v2i for v1i, v2i in zip(v1, v2))\n", "\n", "dot_product(u, v)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "But a *much* more efficient implementation is provided by NumPy with the `np.dot()` function:" ] }, { "cell_type": "code", "execution_count": 23, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "11" ] }, "execution_count": 23, "metadata": {}, "output_type": "execute_result" } ], "source": [ "np.dot(u, v)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Equivalently, you can use the `dot` method of `ndarray`s:" ] }, { "cell_type": "code", "execution_count": 24, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "11" ] }, "execution_count": 24, "metadata": {}, "output_type": "execute_result" } ], "source": [ "u.dot(v)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "**Caution**: the `*` operator will perform an *elementwise* multiplication, *NOT* a dot product:" ] }, { "cell_type": "code", "execution_count": 25, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ " [2 5]\n", "* [3 1] (NOT a dot product)\n", "----------\n" ] }, { "data": { "text/plain": [ "array([6, 5])" ] }, "execution_count": 25, "metadata": {}, "output_type": "execute_result" } ], "source": [ "print(\" \",u)\n", "print(\"* \",v, \"(NOT a dot product)\")\n", "print(\"-\"*10)\n", "\n", "u * v" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### Main properties\n", "* The dot product is **commutative**: $\\textbf{u} \\cdot \\textbf{v} = \\textbf{v} \\cdot \\textbf{u}$.\n", "* The dot product is only defined between two vectors, not between a scalar and a vector. This means that we cannot chain dot products: for example, the expression $\\textbf{u} \\cdot \\textbf{v} \\cdot \\textbf{w}$ is not defined since $\\textbf{u} \\cdot \\textbf{v}$ is a scalar and $\\textbf{w}$ is a vector.\n", "* This also means that the dot product is **NOT associative**: $(\\textbf{u} \\cdot \\textbf{v}) \\cdot \\textbf{w} ≠ \\textbf{u} \\cdot (\\textbf{v} \\cdot \\textbf{w})$ since neither are defined.\n", "* However, the dot product is **associative with regards to scalar multiplication**: $\\lambda \\times (\\textbf{u} \\cdot \\textbf{v}) = (\\lambda \\times \\textbf{u}) \\cdot \\textbf{v} = \\textbf{u} \\cdot (\\lambda \\times \\textbf{v})$\n", "* Finally, the dot product is **distributive** over addition of vectors: $\\textbf{u} \\cdot (\\textbf{v} + \\textbf{w}) = \\textbf{u} \\cdot \\textbf{v} + \\textbf{u} \\cdot \\textbf{w}$." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### Calculating the angle between vectors\n", "One of the many uses of the dot product is to calculate the angle between two non-zero vectors. Looking at the dot product definition, we can deduce the following formula:\n", "\n", "$\\theta = \\arccos{\\left ( \\dfrac{\\textbf{u} \\cdot \\textbf{v}}{\\left \\Vert \\textbf{u} \\right \\| \\times \\left \\Vert \\textbf{v} \\right \\|} \\right ) }$\n", "\n", "Note that if $\\textbf{u} \\cdot \\textbf{v} = 0$, it follows that $\\theta = \\dfrac{π}{2}$. In other words, if the dot product of two non-null vectors is zero, it means that they are orthogonal.\n", "\n", "Let's use this formula to calculate the angle between $\\textbf{u}$ and $\\textbf{v}$ (in radians):" ] }, { "cell_type": "code", "execution_count": 26, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "Angle = 0.8685393952858895 radians\n", " = 49.76364169072618 degrees\n" ] } ], "source": [ "def vector_angle(u, v):\n", " cos_theta = u.dot(v) / LA.norm(u) / LA.norm(v)\n", " return np.arccos(cos_theta.clip(-1, 1))\n", "\n", "theta = vector_angle(u, v)\n", "print(\"Angle =\", theta, \"radians\")\n", "print(\" =\", theta * 180 / np.pi, \"degrees\")" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Note: due to small floating point errors, `cos_theta` may be very slightly outside the $[-1, 1]$ interval, which would make `arccos` fail. This is why we clipped the value within the range, using NumPy's `clip` function." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### Projecting a point onto an axis\n", "The dot product is also very useful to project points onto an axis. The projection of vector $\\textbf{v}$ onto $\\textbf{u}$'s axis is given by this formula:\n", "\n", "$\\textbf{proj}_{\\textbf{u}}{\\textbf{v}} = \\dfrac{\\textbf{u} \\cdot \\textbf{v}}{\\left \\Vert \\textbf{u} \\right \\| ^2} \\times \\textbf{u}$\n", "\n", "Which is equivalent to:\n", "\n", "$\\textbf{proj}_{\\textbf{u}}{\\textbf{v}} = (\\textbf{v} \\cdot \\hat{\\textbf{u}}) \\times \\hat{\\textbf{u}}$\n" ] }, { "cell_type": "code", "execution_count": 27, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "u_normalized = u / LA.norm(u)\n", "proj = v.dot(u_normalized) * u_normalized\n", "\n", "plot_vector2d(u, color=\"r\")\n", "plot_vector2d(v, color=\"b\")\n", "\n", "plot_vector2d(proj, color=\"k\", linestyle=\":\")\n", "plt.plot(proj[0], proj[1], \"ko\")\n", "\n", "plt.plot([proj[0], v[0]], [proj[1], v[1]], \"b:\")\n", "\n", "plt.text(1, 2, \"$proj_u v$\", color=\"k\", fontsize=18)\n", "plt.text(1.8, 0.2, \"$v$\", color=\"b\", fontsize=18)\n", "plt.text(0.8, 3, \"$u$\", color=\"r\", fontsize=18)\n", "\n", "plt.axis([0, 8, 0, 5.5])\n", "plt.gca().set_aspect(\"equal\")\n", "plt.grid()\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "# Matrices\n", "A matrix is a rectangular array of scalars (i.e. any number: integer, real or complex) arranged in rows and columns, for example:\n", "\n", "\\begin{bmatrix} 10 & 20 & 30 \\\\ 40 & 50 & 60 \\end{bmatrix}\n", "\n", "You can also think of a matrix as a list of vectors: the previous matrix contains either 2 horizontal 3D vectors or 3 vertical 2D vectors.\n", "\n", "Matrices are convenient and very efficient to run operations on many vectors at a time. We will also see that they are great at representing and performing linear transformations such rotations, translations and scaling." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Matrices in python\n", "In python, a matrix can be represented in various ways. The simplest is just a list of python lists:" ] }, { "cell_type": "code", "execution_count": 28, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "[[10, 20, 30], [40, 50, 60]]" ] }, "execution_count": 28, "metadata": {}, "output_type": "execute_result" } ], "source": [ "[\n", " [10, 20, 30],\n", " [40, 50, 60]\n", "]" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "A much more efficient way is to use the NumPy library which provides optimized implementations of many matrix operations:" ] }, { "cell_type": "code", "execution_count": 29, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[10, 20, 30],\n", " [40, 50, 60]])" ] }, "execution_count": 29, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A = np.array([\n", " [10,20,30],\n", " [40,50,60]\n", "])\n", "A" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "By convention matrices generally have uppercase names, such as $A$.\n", "\n", "In the rest of this tutorial, we will assume that we are using NumPy arrays (type `ndarray`) to represent matrices." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Size\n", "The size of a matrix is defined by its number of rows and number of columns. It is noted $rows \\times columns$. For example, the matrix $A$ above is an example of a $2 \\times 3$ matrix: 2 rows, 3 columns. Caution: a $3 \\times 2$ matrix would have 3 rows and 2 columns.\n", "\n", "To get a matrix's size in NumPy:" ] }, { "cell_type": "code", "execution_count": 30, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "(2, 3)" ] }, "execution_count": 30, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A.shape" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "**Caution**: the `size` attribute represents the number of elements in the `ndarray`, not the matrix's size:" ] }, { "cell_type": "code", "execution_count": 31, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "6" ] }, "execution_count": 31, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A.size" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Element indexing\n", "The number located in the $i^{th}$ row, and $j^{th}$ column of a matrix $X$ is sometimes noted $X_{i,j}$ or $X_{ij}$, but there is no standard notation, so people often prefer to explicitly name the elements, like this: \"*let $X = (x_{i,j})_{1 ≤ i ≤ m, 1 ≤ j ≤ n}$*\". This means that $X$ is equal to:\n", "\n", "$X = \\begin{bmatrix}\n", " x_{1,1} & x_{1,2} & x_{1,3} & \\cdots & x_{1,n}\\\\\n", " x_{2,1} & x_{2,2} & x_{2,3} & \\cdots & x_{2,n}\\\\\n", " x_{3,1} & x_{3,2} & x_{3,3} & \\cdots & x_{3,n}\\\\\n", " \\vdots & \\vdots & \\vdots & \\ddots & \\vdots \\\\\n", " x_{m,1} & x_{m,2} & x_{m,3} & \\cdots & x_{m,n}\\\\\n", "\\end{bmatrix}$\n", "\n", "However, in this notebook we will use the $X_{i,j}$ notation, as it matches fairly well NumPy's notation. Note that in math indices generally start at 1, but in programming they usually start at 0. So to access $A_{2,3}$ programmatically, we need to write this:" ] }, { "cell_type": "code", "execution_count": 32, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "60" ] }, "execution_count": 32, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A[1,2] # 2nd row, 3rd column" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The $i^{th}$ row vector is sometimes noted $M_i$ or $M_{i,*}$, but again there is no standard notation so people often prefer to explicitly define their own names, for example: \"*let **x**$_{i}$ be the $i^{th}$ row vector of matrix $X$*\". We will use the $M_{i,*}$, for the same reason as above. For example, to access $A_{2,*}$ (i.e. $A$'s 2nd row vector):" ] }, { "cell_type": "code", "execution_count": 33, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([40, 50, 60])" ] }, "execution_count": 33, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A[1, :] # 2nd row vector (as a 1D array)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Similarly, the $j^{th}$ column vector is sometimes noted $M^j$ or $M_{*,j}$, but there is no standard notation. We will use $M_{*,j}$. For example, to access $A_{*,3}$ (i.e. $A$'s 3rd column vector):" ] }, { "cell_type": "code", "execution_count": 34, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([30, 60])" ] }, "execution_count": 34, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A[:, 2] # 3rd column vector (as a 1D array)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Note that the result is actually a one-dimensional NumPy array: there is no such thing as a *vertical* or *horizontal* one-dimensional array. If you need to actually represent a row vector as a one-row matrix (i.e. a 2D NumPy array), or a column vector as a one-column matrix, then you need to use a slice instead of an integer when accessing the row or column, for example:" ] }, { "cell_type": "code", "execution_count": 35, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[40, 50, 60]])" ] }, "execution_count": 35, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A[1:2, :] # rows 2 to 3 (excluded): this returns row 2 as a one-row matrix" ] }, { "cell_type": "code", "execution_count": 36, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[30],\n", " [60]])" ] }, "execution_count": 36, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A[:, 2:3] # columns 3 to 4 (excluded): this returns column 3 as a one-column matrix" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Square, triangular, diagonal and identity matrices\n", "A **square matrix** is a matrix that has the same number of rows and columns, for example a $3 \\times 3$ matrix:\n", "\n", "\\begin{bmatrix}\n", " 4 & 9 & 2 \\\\\n", " 3 & 5 & 7 \\\\\n", " 8 & 1 & 6\n", "\\end{bmatrix}" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "An **upper triangular matrix** is a special kind of square matrix where all the elements *below* the main diagonal (top-left to bottom-right) are zero, for example:\n", "\n", "\\begin{bmatrix}\n", " 4 & 9 & 2 \\\\\n", " 0 & 5 & 7 \\\\\n", " 0 & 0 & 6\n", "\\end{bmatrix}" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Similarly, a **lower triangular matrix** is a square matrix where all elements *above* the main diagonal are zero, for example:\n", "\n", "\\begin{bmatrix}\n", " 4 & 0 & 0 \\\\\n", " 3 & 5 & 0 \\\\\n", " 8 & 1 & 6\n", "\\end{bmatrix}" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "A **triangular matrix** is one that is either lower triangular or upper triangular." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "A matrix that is both upper and lower triangular is called a **diagonal matrix**, for example:\n", "\n", "\\begin{bmatrix}\n", " 4 & 0 & 0 \\\\\n", " 0 & 5 & 0 \\\\\n", " 0 & 0 & 6\n", "\\end{bmatrix}\n", "\n", "You can construct a diagonal matrix using NumPy's `diag` function:" ] }, { "cell_type": "code", "execution_count": 37, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[4, 0, 0],\n", " [0, 5, 0],\n", " [0, 0, 6]])" ] }, "execution_count": 37, "metadata": {}, "output_type": "execute_result" } ], "source": [ "np.diag([4, 5, 6])" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "If you pass a matrix to the `diag` function, it will happily extract the diagonal values:" ] }, { "cell_type": "code", "execution_count": 38, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([1, 5, 9])" ] }, "execution_count": 38, "metadata": {}, "output_type": "execute_result" } ], "source": [ "D = np.array([\n", " [1, 2, 3],\n", " [4, 5, 6],\n", " [7, 8, 9],\n", " ])\n", "np.diag(D)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Finally, the **identity matrix** of size $n$, noted $I_n$, is a diagonal matrix of size $n \\times n$ with $1$'s in the main diagonal, for example $I_3$:\n", "\n", "\\begin{bmatrix}\n", " 1 & 0 & 0 \\\\\n", " 0 & 1 & 0 \\\\\n", " 0 & 0 & 1\n", "\\end{bmatrix}\n", "\n", "Numpy's `eye` function returns the identity matrix of the desired size:" ] }, { "cell_type": "code", "execution_count": 39, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[1., 0., 0.],\n", " [0., 1., 0.],\n", " [0., 0., 1.]])" ] }, "execution_count": 39, "metadata": {}, "output_type": "execute_result" } ], "source": [ "np.eye(3)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The identity matrix is often noted simply $I$ (instead of $I_n$) when its size is clear given the context. It is called the *identity* matrix because multiplying a matrix with it leaves the matrix unchanged as we will see below." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Adding matrices\n", "If two matrices $Q$ and $R$ have the same size $m \\times n$, they can be added together. Addition is performed *elementwise*: the result is also an $m \\times n$ matrix $S$ where each element is the sum of the elements at the corresponding position: $S_{i,j} = Q_{i,j} + R_{i,j}$\n", "\n", "$S =\n", "\\begin{bmatrix}\n", " Q_{11} + R_{11} & Q_{12} + R_{12} & Q_{13} + R_{13} & \\cdots & Q_{1n} + R_{1n} \\\\\n", " Q_{21} + R_{21} & Q_{22} + R_{22} & Q_{23} + R_{23} & \\cdots & Q_{2n} + R_{2n} \\\\\n", " Q_{31} + R_{31} & Q_{32} + R_{32} & Q_{33} + R_{33} & \\cdots & Q_{3n} + R_{3n} \\\\\n", " \\vdots & \\vdots & \\vdots & \\ddots & \\vdots \\\\\n", " Q_{m1} + R_{m1} & Q_{m2} + R_{m2} & Q_{m3} + R_{m3} & \\cdots & Q_{mn} + R_{mn} \\\\\n", "\\end{bmatrix}$\n", "\n", "For example, let's create a $2 \\times 3$ matrix $B$ and compute $A + B$:" ] }, { "cell_type": "code", "execution_count": 40, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[1, 2, 3],\n", " [4, 5, 6]])" ] }, "execution_count": 40, "metadata": {}, "output_type": "execute_result" } ], "source": [ "B = np.array([[1, 2, 3], [4, 5, 6]])\n", "B" ] }, { "cell_type": "code", "execution_count": 41, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[10, 20, 30],\n", " [40, 50, 60]])" ] }, "execution_count": 41, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A" ] }, { "cell_type": "code", "execution_count": 42, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[11, 22, 33],\n", " [44, 55, 66]])" ] }, "execution_count": 42, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A + B" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "**Addition is *commutative***, meaning that $A + B = B + A$:" ] }, { "cell_type": "code", "execution_count": 43, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[11, 22, 33],\n", " [44, 55, 66]])" ] }, "execution_count": 43, "metadata": {}, "output_type": "execute_result" } ], "source": [ "B + A" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "**It is also *associative***, meaning that $A + (B + C) = (A + B) + C$:" ] }, { "cell_type": "code", "execution_count": 44, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[111, 222, 333],\n", " [444, 555, 666]])" ] }, "execution_count": 44, "metadata": {}, "output_type": "execute_result" } ], "source": [ "C = np.array([[100, 200, 300], [400, 500, 600]])\n", "\n", "A + (B + C)" ] }, { "cell_type": "code", "execution_count": 45, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[111, 222, 333],\n", " [444, 555, 666]])" ] }, "execution_count": 45, "metadata": {}, "output_type": "execute_result" } ], "source": [ "(A + B) + C" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Scalar multiplication\n", "A matrix $M$ can be multiplied by a scalar $\\lambda$. The result is noted $\\lambda M$, and it is a matrix of the same size as $M$ with all elements multiplied by $\\lambda$:\n", "\n", "$\\lambda M =\n", "\\begin{bmatrix}\n", " \\lambda \\times M_{11} & \\lambda \\times M_{12} & \\lambda \\times M_{13} & \\cdots & \\lambda \\times M_{1n} \\\\\n", " \\lambda \\times M_{21} & \\lambda \\times M_{22} & \\lambda \\times M_{23} & \\cdots & \\lambda \\times M_{2n} \\\\\n", " \\lambda \\times M_{31} & \\lambda \\times M_{32} & \\lambda \\times M_{33} & \\cdots & \\lambda \\times M_{3n} \\\\\n", " \\vdots & \\vdots & \\vdots & \\ddots & \\vdots \\\\\n", " \\lambda \\times M_{m1} & \\lambda \\times M_{m2} & \\lambda \\times M_{m3} & \\cdots & \\lambda \\times M_{mn} \\\\\n", "\\end{bmatrix}$\n", "\n", "A more concise way of writing this is:\n", "\n", "$(\\lambda M)_{i,j} = \\lambda (M)_{i,j}$\n", "\n", "In NumPy, simply use the `*` operator to multiply a matrix by a scalar. For example:" ] }, { "cell_type": "code", "execution_count": 46, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[ 20, 40, 60],\n", " [ 80, 100, 120]])" ] }, "execution_count": 46, "metadata": {}, "output_type": "execute_result" } ], "source": [ "2 * A" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Scalar multiplication is also defined on the right-hand side, and gives the same result: $M \\lambda = \\lambda M$. For example:" ] }, { "cell_type": "code", "execution_count": 47, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[ 20, 40, 60],\n", " [ 80, 100, 120]])" ] }, "execution_count": 47, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A * 2" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "This makes scalar multiplication **commutative**.\n", "\n", "It is also **associative**, meaning that $\\alpha (\\beta M) = (\\alpha \\times \\beta) M$, where $\\alpha$ and $\\beta$ are scalars. For example:" ] }, { "cell_type": "code", "execution_count": 48, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[ 60, 120, 180],\n", " [240, 300, 360]])" ] }, "execution_count": 48, "metadata": {}, "output_type": "execute_result" } ], "source": [ "2 * (3 * A)" ] }, { "cell_type": "code", "execution_count": 49, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[ 60, 120, 180],\n", " [240, 300, 360]])" ] }, "execution_count": 49, "metadata": {}, "output_type": "execute_result" } ], "source": [ "(2 * 3) * A" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Finally, it is **distributive over addition** of matrices, meaning that $\\lambda (Q + R) = \\lambda Q + \\lambda R$:" ] }, { "cell_type": "code", "execution_count": 50, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[ 22, 44, 66],\n", " [ 88, 110, 132]])" ] }, "execution_count": 50, "metadata": {}, "output_type": "execute_result" } ], "source": [ "2 * (A + B)" ] }, { "cell_type": "code", "execution_count": 51, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[ 22, 44, 66],\n", " [ 88, 110, 132]])" ] }, "execution_count": 51, "metadata": {}, "output_type": "execute_result" } ], "source": [ "2 * A + 2 * B" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Matrix multiplication\n", "So far, matrix operations have been rather intuitive. But multiplying matrices is a bit more involved.\n", "\n", "A matrix $Q$ of size $m \\times n$ can be multiplied by a matrix $R$ of size $n \\times q$. It is noted simply $QR$ without multiplication sign or dot. The result $P$ is an $m \\times q$ matrix where each element is computed as a sum of products:\n", "\n", "$P_{i,j} = \\sum_{k=1}^n{Q_{i,k} \\times R_{k,j}}$\n", "\n", "The element at position $i,j$ in the resulting matrix is the sum of the products of elements in row $i$ of matrix $Q$ by the elements in column $j$ of matrix $R$.\n", "\n", "$P =\n", "\\begin{bmatrix}\n", "Q_{11} R_{11} + Q_{12} R_{21} + \\cdots + Q_{1n} R_{n1} &\n", " Q_{11} R_{12} + Q_{12} R_{22} + \\cdots + Q_{1n} R_{n2} &\n", " \\cdots &\n", " Q_{11} R_{1q} + Q_{12} R_{2q} + \\cdots + Q_{1n} R_{nq} \\\\\n", "Q_{21} R_{11} + Q_{22} R_{21} + \\cdots + Q_{2n} R_{n1} &\n", " Q_{21} R_{12} + Q_{22} R_{22} + \\cdots + Q_{2n} R_{n2} &\n", " \\cdots &\n", " Q_{21} R_{1q} + Q_{22} R_{2q} + \\cdots + Q_{2n} R_{nq} \\\\\n", " \\vdots & \\vdots & \\ddots & \\vdots \\\\\n", "Q_{m1} R_{11} + Q_{m2} R_{21} + \\cdots + Q_{mn} R_{n1} &\n", " Q_{m1} R_{12} + Q_{m2} R_{22} + \\cdots + Q_{mn} R_{n2} &\n", " \\cdots &\n", " Q_{m1} R_{1q} + Q_{m2} R_{2q} + \\cdots + Q_{mn} R_{nq}\n", "\\end{bmatrix}$\n", "\n", "You may notice that each element $P_{i,j}$ is the dot product of the row vector $Q_{i,*}$ and the column vector $R_{*,j}$:\n", "\n", "$P_{i,j} = Q_{i,*} \\cdot R_{*,j}$\n", "\n", "So we can rewrite $P$ more concisely as:\n", "\n", "$P =\n", "\\begin{bmatrix}\n", "Q_{1,*} \\cdot R_{*,1} & Q_{1,*} \\cdot R_{*,2} & \\cdots & Q_{1,*} \\cdot R_{*,q} \\\\\n", "Q_{2,*} \\cdot R_{*,1} & Q_{2,*} \\cdot R_{*,2} & \\cdots & Q_{2,*} \\cdot R_{*,q} \\\\\n", "\\vdots & \\vdots & \\ddots & \\vdots \\\\\n", "Q_{m,*} \\cdot R_{*,1} & Q_{m,*} \\cdot R_{*,2} & \\cdots & Q_{m,*} \\cdot R_{*,q}\n", "\\end{bmatrix}$\n" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Let's multiply two matrices in NumPy, using `ndarray`'s `np.matmul()` function:\n", "\n", "$E = AD = \\begin{bmatrix}\n", " 10 & 20 & 30 \\\\\n", " 40 & 50 & 60\n", "\\end{bmatrix} \n", "\\begin{bmatrix}\n", " 2 & 3 & 5 & 7 \\\\\n", " 11 & 13 & 17 & 19 \\\\\n", " 23 & 29 & 31 & 37\n", "\\end{bmatrix} = \n", "\\begin{bmatrix}\n", " 930 & 1160 & 1320 & 1560 \\\\\n", " 2010 & 2510 & 2910 & 3450\n", "\\end{bmatrix}$" ] }, { "cell_type": "code", "execution_count": 52, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[ 930, 1160, 1320, 1560],\n", " [2010, 2510, 2910, 3450]])" ] }, "execution_count": 52, "metadata": {}, "output_type": "execute_result" } ], "source": [ "D = np.array([\n", " [ 2, 3, 5, 7],\n", " [11, 13, 17, 19],\n", " [23, 29, 31, 37]\n", " ])\n", "E = np.matmul(A, D)\n", "E" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Python 3.5 [introduced](https://docs.python.org/3/whatsnew/3.5.html#pep-465-a-dedicated-infix-operator-for-matrix-multiplication) the `@` infix operator for matrix multiplication, and NumPy 1.10 added support for it. `A @ D` is equivalent to `np.matmul(A, D)`:" ] }, { "cell_type": "code", "execution_count": 53, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[ 930, 1160, 1320, 1560],\n", " [2010, 2510, 2910, 3450]])" ] }, "execution_count": 53, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A @ D" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The `@` operator also works for vectors. `u @ v` computes the dot product of `u` and `v`:" ] }, { "cell_type": "code", "execution_count": 54, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "11" ] }, "execution_count": 54, "metadata": {}, "output_type": "execute_result" } ], "source": [ "u @ v" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Let's check this result by looking at one element, just to be sure. To calculate $E_{2,3}$ for example, we need to multiply elements in $A$'s $2^{nd}$ row by elements in $D$'s $3^{rd}$ column, and sum up these products:" ] }, { "cell_type": "code", "execution_count": 55, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "2910" ] }, "execution_count": 55, "metadata": {}, "output_type": "execute_result" } ], "source": [ "40*5 + 50*17 + 60*31" ] }, { "cell_type": "code", "execution_count": 56, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "2910" ] }, "execution_count": 56, "metadata": {}, "output_type": "execute_result" } ], "source": [ "E[1,2] # row 2, column 3" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Looks good! You can check the other elements until you get used to the algorithm.\n", "\n", "We multiplied a $2 \\times 3$ matrix by a $3 \\times 4$ matrix, so the result is a $2 \\times 4$ matrix. The first matrix's number of columns has to be equal to the second matrix's number of rows. If we try to multiply $D$ by $A$, we get an error because D has 4 columns while A has 2 rows:" ] }, { "cell_type": "code", "execution_count": 57, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "ValueError: matmul: Input operand 1 has a mismatch in its core dimension 0, with gufunc signature (n?,k),(k,m?)->(n?,m?) (size 2 is different from 4)\n" ] } ], "source": [ "try:\n", " D @ A\n", "except ValueError as e:\n", " print(\"ValueError:\", e)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "This illustrates the fact that **matrix multiplication is *NOT* commutative**: in general $QR ≠ RQ$.\n", "\n", "In fact, $QR$ and $RQ$ are only *both* defined if $Q$ has size $m \\times n$ and $R$ has size $n \\times m$. Let's look at an example where both *are* defined and show that they are (in general) *NOT* equal:" ] }, { "cell_type": "code", "execution_count": 58, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[400, 130],\n", " [940, 310]])" ] }, "execution_count": 58, "metadata": {}, "output_type": "execute_result" } ], "source": [ "F = np.array([\n", " [5,2],\n", " [4,1],\n", " [9,3]\n", " ])\n", "A @ F" ] }, { "cell_type": "code", "execution_count": 59, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[130, 200, 270],\n", " [ 80, 130, 180],\n", " [210, 330, 450]])" ] }, "execution_count": 59, "metadata": {}, "output_type": "execute_result" } ], "source": [ "F @ A" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "On the other hand, **matrix multiplication *is* associative**, meaning that $Q(RS) = (QR)S$. Let's create a $4 \\times 5$ matrix $G$ to illustrate this:" ] }, { "cell_type": "code", "execution_count": 60, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[21640, 28390, 27320, 31140, 13570],\n", " [47290, 62080, 60020, 68580, 29500]])" ] }, "execution_count": 60, "metadata": {}, "output_type": "execute_result" } ], "source": [ "G = np.array([\n", " [8, 7, 4, 2, 5],\n", " [2, 5, 1, 0, 5],\n", " [9, 11, 17, 21, 0],\n", " [0, 1, 0, 1, 2]])\n", "(A @ D) @ G # (AD)G" ] }, { "cell_type": "code", "execution_count": 61, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[21640, 28390, 27320, 31140, 13570],\n", " [47290, 62080, 60020, 68580, 29500]])" ] }, "execution_count": 61, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A @ (D @ G) # A(DG)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "It is also ***distributive* over addition** of matrices, meaning that $(Q + R)S = QS + RS$. For example:" ] }, { "cell_type": "code", "execution_count": 62, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[1023, 1276, 1452, 1716],\n", " [2211, 2761, 3201, 3795]])" ] }, "execution_count": 62, "metadata": {}, "output_type": "execute_result" } ], "source": [ "(A + B) @ D" ] }, { "cell_type": "code", "execution_count": 63, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[1023, 1276, 1452, 1716],\n", " [2211, 2761, 3201, 3795]])" ] }, "execution_count": 63, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A @ D + B @ D" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The product of a matrix $M$ by the identity matrix (of matching size) results in the same matrix $M$. More formally, if $M$ is an $m \\times n$ matrix, then:\n", "\n", "$M I_n = I_m M = M$\n", "\n", "This is generally written more concisely (since the size of the identity matrices is unambiguous given the context):\n", "\n", "$MI = IM = M$\n", "\n", "For example:" ] }, { "cell_type": "code", "execution_count": 64, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[10., 20., 30.],\n", " [40., 50., 60.]])" ] }, "execution_count": 64, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A @ np.eye(3)" ] }, { "cell_type": "code", "execution_count": 65, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[10., 20., 30.],\n", " [40., 50., 60.]])" ] }, "execution_count": 65, "metadata": {}, "output_type": "execute_result" } ], "source": [ "np.eye(2) @ A" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "**Caution**: NumPy's `*` operator performs elementwise multiplication, *NOT* a matrix multiplication:" ] }, { "cell_type": "code", "execution_count": 66, "metadata": { "scrolled": true }, "outputs": [ { "data": { "text/plain": [ "array([[ 10, 40, 90],\n", " [160, 250, 360]])" ] }, "execution_count": 66, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A * B # NOT a matrix multiplication" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Matrix transpose\n", "The transpose of a matrix $M$ is a matrix noted $M^T$ such that the $i^{th}$ row in $M^T$ is equal to the $i^{th}$ column in $M$:\n", "\n", "$ A^T =\n", "\\begin{bmatrix}\n", " 10 & 20 & 30 \\\\\n", " 40 & 50 & 60\n", "\\end{bmatrix}^T =\n", "\\begin{bmatrix}\n", " 10 & 40 \\\\\n", " 20 & 50 \\\\\n", " 30 & 60\n", "\\end{bmatrix}$\n", "\n", "In other words, ($A^T)_{i,j}$ = $A_{j,i}$\n", "\n", "Obviously, if $M$ is an $m \\times n$ matrix, then $M^T$ is an $n \\times m$ matrix.\n", "\n", "Note: there are a few other notations, such as $M^t$, $M′$, or ${^t}M$.\n", "\n", "In NumPy, a matrix's transpose can be obtained simply using the `T` attribute:" ] }, { "cell_type": "code", "execution_count": 67, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[10, 20, 30],\n", " [40, 50, 60]])" ] }, "execution_count": 67, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A" ] }, { "cell_type": "code", "execution_count": 68, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[10, 40],\n", " [20, 50],\n", " [30, 60]])" ] }, "execution_count": 68, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A.T" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "As you might expect, transposing a matrix twice returns the original matrix:" ] }, { "cell_type": "code", "execution_count": 69, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[10, 20, 30],\n", " [40, 50, 60]])" ] }, "execution_count": 69, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A.T.T" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Transposition is distributive over addition of matrices, meaning that $(Q + R)^T = Q^T + R^T$. For example:" ] }, { "cell_type": "code", "execution_count": 70, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[11, 44],\n", " [22, 55],\n", " [33, 66]])" ] }, "execution_count": 70, "metadata": {}, "output_type": "execute_result" } ], "source": [ "(A + B).T" ] }, { "cell_type": "code", "execution_count": 71, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[11, 44],\n", " [22, 55],\n", " [33, 66]])" ] }, "execution_count": 71, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A.T + B.T" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Moreover, $(Q \\cdot R)^T = R^T \\cdot Q^T$. Note that the order is reversed. For example:" ] }, { "cell_type": "code", "execution_count": 72, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[ 930, 2010],\n", " [1160, 2510],\n", " [1320, 2910],\n", " [1560, 3450]])" ] }, "execution_count": 72, "metadata": {}, "output_type": "execute_result" } ], "source": [ "(A @ D).T" ] }, { "cell_type": "code", "execution_count": 73, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[ 930, 2010],\n", " [1160, 2510],\n", " [1320, 2910],\n", " [1560, 3450]])" ] }, "execution_count": 73, "metadata": {}, "output_type": "execute_result" } ], "source": [ "D.T @ A.T" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "A **symmetric matrix** $M$ is defined as a matrix that is equal to its transpose: $M^T = M$. This definition implies that it must be a square matrix whose elements are symmetric relative to the main diagonal, for example:\n", "\n", "\\begin{bmatrix}\n", " 17 & 22 & 27 & 49 \\\\\n", " 22 & 29 & 36 & 0 \\\\\n", " 27 & 36 & 45 & 2 \\\\\n", " 49 & 0 & 2 & 99\n", "\\end{bmatrix}\n", "\n", "The product of a matrix by its transpose is always a symmetric matrix, for example:" ] }, { "cell_type": "code", "execution_count": 74, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[ 87, 279, 547],\n", " [ 279, 940, 1860],\n", " [ 547, 1860, 3700]])" ] }, "execution_count": 74, "metadata": {}, "output_type": "execute_result" } ], "source": [ "D @ D.T" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Converting 1D arrays to 2D arrays in NumPy\n", "As we mentioned earlier, in NumPy (as opposed to Matlab, for example), 1D really means 1D: there is no such thing as a vertical 1D-array or a horizontal 1D-array. So you should not be surprised to see that transposing a 1D array does not do anything:" ] }, { "cell_type": "code", "execution_count": 75, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([2, 5])" ] }, "execution_count": 75, "metadata": {}, "output_type": "execute_result" } ], "source": [ "u" ] }, { "cell_type": "code", "execution_count": 76, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([2, 5])" ] }, "execution_count": 76, "metadata": {}, "output_type": "execute_result" } ], "source": [ "u.T" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "We want to convert $\\textbf{u}$ into a row vector before transposing it. There are a few ways to do this:" ] }, { "cell_type": "code", "execution_count": 77, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[2, 5]])" ] }, "execution_count": 77, "metadata": {}, "output_type": "execute_result" } ], "source": [ "u_row = np.array([u])\n", "u_row" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Notice the extra square brackets: this is a 2D array with just one row (i.e. a $1 \\times 2$ matrix). In other words, it really is a **row vector**." ] }, { "cell_type": "code", "execution_count": 78, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[2, 5]])" ] }, "execution_count": 78, "metadata": {}, "output_type": "execute_result" } ], "source": [ "u[np.newaxis, :]" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "This is quite explicit: we are asking for a new vertical axis, keeping the existing data as the horizontal axis." ] }, { "cell_type": "code", "execution_count": 79, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[2, 5]])" ] }, "execution_count": 79, "metadata": {}, "output_type": "execute_result" } ], "source": [ "u[np.newaxis]" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "This is equivalent, but a little less explicit." ] }, { "cell_type": "code", "execution_count": 80, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[2, 5]])" ] }, "execution_count": 80, "metadata": {}, "output_type": "execute_result" } ], "source": [ "u[None]" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "This is the shortest version, but you probably want to avoid it because it is unclear. The reason it works is that `np.newaxis` is actually equal to `None`, so this is equivalent to the previous version.\n", "\n", "Ok, now let's transpose our row vector:" ] }, { "cell_type": "code", "execution_count": 81, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[2],\n", " [5]])" ] }, "execution_count": 81, "metadata": {}, "output_type": "execute_result" } ], "source": [ "u_row.T" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Great! We now have a nice **column vector**.\n", "\n", "Rather than creating a row vector then transposing it, it is also possible to convert a 1D array directly into a column vector:" ] }, { "cell_type": "code", "execution_count": 82, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[2],\n", " [5]])" ] }, "execution_count": 82, "metadata": {}, "output_type": "execute_result" } ], "source": [ "u[:, np.newaxis]" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Plotting a matrix\n", "We have already seen that vectors can be represented as points or arrows in N-dimensional space. Is there a good graphical representation of matrices? Well you can simply see a matrix as a list of vectors, so plotting a matrix results in many points or arrows. For example, let's create a $2 \\times 4$ matrix `P` and plot it as points:" ] }, { "cell_type": "code", "execution_count": 83, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "P = np.array([\n", " [3.0, 4.0, 1.0, 4.6],\n", " [0.2, 3.5, 2.0, 0.5]\n", " ])\n", "x_coords_P, y_coords_P = P\n", "plt.scatter(x_coords_P, y_coords_P)\n", "plt.axis([0, 5, 0, 4])\n", "plt.gca().set_aspect(\"equal\")\n", "plt.grid()\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Of course, we could also have stored the same 4 vectors as row vectors instead of column vectors, resulting in a $4 \\times 2$ matrix (the transpose of $P$, in fact). It is really an arbitrary choice.\n", "\n", "Since the vectors are ordered, you can see the matrix as a path and represent it with connected dots:" ] }, { "cell_type": "code", "execution_count": 84, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "plt.plot(x_coords_P, y_coords_P, \"bo\")\n", "plt.plot(x_coords_P, y_coords_P, \"b--\")\n", "plt.axis([0, 5, 0, 4])\n", "plt.gca().set_aspect(\"equal\")\n", "plt.grid()\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Or you can represent it as a polygon: matplotlib's `Polygon` class expects an $n \\times 2$ NumPy array, not a $2 \\times n$ array, so we just need to give it $P^T$:" ] }, { "cell_type": "code", "execution_count": 85, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "from matplotlib.patches import Polygon\n", "plt.gca().add_artist(Polygon(P.T))\n", "plt.axis([0, 5, 0, 4])\n", "plt.gca().set_aspect(\"equal\")\n", "plt.grid()\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Geometric applications of matrix operations\n", "We saw earlier that vector addition results in a geometric translation, vector multiplication by a scalar results in rescaling (zooming in or out, centered on the origin), and vector dot product results in projecting a vector onto another vector, rescaling and measuring the resulting coordinate.\n", "\n", "Similarly, matrix operations have very useful geometric applications." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### Addition = multiple geometric translations\n", "First, adding two matrices together is equivalent to adding all their vectors together. For example, let's create a $2 \\times 4$ matrix $H$ and add it to $P$, and look at the result:" ] }, { "cell_type": "code", "execution_count": 86, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "H = np.array([\n", " [ 0.5, -0.2, 0.2, -0.1],\n", " [ 0.4, 0.4, 1.5, 0.6]\n", " ])\n", "P_moved = P + H\n", "\n", "plt.gca().add_artist(Polygon(P.T, alpha=0.2))\n", "plt.gca().add_artist(Polygon(P_moved.T, alpha=0.3, color=\"r\"))\n", "for vector, origin in zip(H.T, P.T):\n", " plot_vector2d(vector, origin=origin)\n", "\n", "plt.text(2.2, 1.8, \"$P$\", color=\"b\", fontsize=18)\n", "plt.text(2.0, 3.2, \"$P+H$\", color=\"r\", fontsize=18)\n", "plt.text(2.5, 0.5, \"$H_{*,1}$\", color=\"k\", fontsize=18)\n", "plt.text(4.1, 3.5, \"$H_{*,2}$\", color=\"k\", fontsize=18)\n", "plt.text(0.4, 2.6, \"$H_{*,3}$\", color=\"k\", fontsize=18)\n", "plt.text(4.3, 0.2, \"$H_{*,4}$\", color=\"k\", fontsize=18)\n", "\n", "plt.axis([0, 5, 0, 4])\n", "plt.gca().set_aspect(\"equal\")\n", "plt.grid()\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "If we add a matrix full of identical vectors, we get a simple geometric translation:" ] }, { "cell_type": "code", "execution_count": 87, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "H2 = np.array([\n", " [-0.5, -0.5, -0.5, -0.5],\n", " [ 0.4, 0.4, 0.4, 0.4]\n", " ])\n", "P_translated = P + H2\n", "\n", "plt.gca().add_artist(Polygon(P.T, alpha=0.2))\n", "plt.gca().add_artist(Polygon(P_translated.T, alpha=0.3, color=\"r\"))\n", "for vector, origin in zip(H2.T, P.T):\n", " plot_vector2d(vector, origin=origin)\n", "\n", "plt.axis([0, 5, 0, 4])\n", "plt.gca().set_aspect(\"equal\")\n", "plt.grid()\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Although matrices can only be added together if they have the same size, NumPy allows adding a row vector or a column vector to a matrix: this is called *broadcasting* and is explained in further details in the [NumPy tutorial](tools_numpy.ipynb). We could have obtained the same result as above with:" ] }, { "cell_type": "code", "execution_count": 88, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[2.5, 3.5, 0.5, 4.1],\n", " [0.6, 3.9, 2.4, 0.9]])" ] }, "execution_count": 88, "metadata": {}, "output_type": "execute_result" } ], "source": [ "P + [[-0.5], [0.4]] # same as P + H2, thanks to NumPy broadcasting" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### Scalar multiplication\n", "Multiplying a matrix by a scalar results in all its vectors being multiplied by that scalar, so unsurprisingly, the geometric result is a rescaling of the entire figure. For example, let's rescale our polygon by a factor of 60% (zooming out, centered on the origin):" ] }, { "cell_type": "code", "execution_count": 89, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "def plot_transformation(P_before, P_after, text_before, text_after, axis = [0, 5, 0, 4], arrows=False):\n", " if arrows:\n", " for vector_before, vector_after in zip(P_before.T, P_after.T):\n", " plot_vector2d(vector_before, color=\"blue\", linestyle=\"--\")\n", " plot_vector2d(vector_after, color=\"red\", linestyle=\"-\")\n", " plt.gca().add_artist(Polygon(P_before.T, alpha=0.2))\n", " plt.gca().add_artist(Polygon(P_after.T, alpha=0.3, color=\"r\"))\n", " plt.plot(P_before[0], P_before[1], \"b--\", alpha=0.5)\n", " plt.plot(P_after[0], P_after[1], \"r--\", alpha=0.5)\n", " plt.text(P_before[0].mean(), P_before[1].mean(), text_before, fontsize=18, color=\"blue\")\n", " plt.text(P_after[0].mean(), P_after[1].mean(), text_after, fontsize=18, color=\"red\")\n", " plt.axis(axis)\n", " plt.gca().set_aspect(\"equal\")\n", " plt.grid()\n", "\n", "P_rescaled = 0.60 * P\n", "plot_transformation(P, P_rescaled, \"$P$\", \"$0.6 P$\", arrows=True)\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### Matrix multiplication – Projection onto an axis\n", "Matrix multiplication is more complex to visualize, but it is also the most powerful tool in the box.\n", "\n", "Let's start simple, by defining a $1 \\times 2$ matrix $U = \\begin{bmatrix} 1 & 0 \\end{bmatrix}$. This row vector is just the horizontal unit vector." ] }, { "cell_type": "code", "execution_count": 90, "metadata": {}, "outputs": [], "source": [ "U = np.array([[1, 0]])" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Now let's look at the dot product $U \\cdot P$:" ] }, { "cell_type": "code", "execution_count": 91, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[3. , 4. , 1. , 4.6]])" ] }, "execution_count": 91, "metadata": {}, "output_type": "execute_result" } ], "source": [ "U @ P" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "These are the horizontal coordinates of the vectors in $P$. In other words, we just projected $P$ onto the horizontal axis:" ] }, { "cell_type": "code", "execution_count": 92, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "def plot_projection(U, P):\n", " U_P = U @ P\n", " \n", " axis_end = 100 * U\n", " plot_vector2d(axis_end[0], color=\"black\")\n", "\n", " plt.gca().add_artist(Polygon(P.T, alpha=0.2))\n", " for vector, proj_coordinate in zip(P.T, U_P.T):\n", " proj_point = proj_coordinate * U\n", " plt.plot(proj_point[0][0], proj_point[0][1], \"ro\", zorder=10)\n", " plt.plot([vector[0], proj_point[0][0]], [vector[1], proj_point[0][1]],\n", " \"r--\", zorder=10)\n", "\n", " plt.axis([0, 5, 0, 4])\n", " plt.gca().set_aspect(\"equal\")\n", " plt.grid()\n", " plt.show()\n", "\n", "plot_projection(U, P)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "We can actually project on any other axis by just replacing $U$ with any other unit vector. For example, let's project on the axis that is at a 30° angle above the horizontal axis:" ] }, { "cell_type": "code", "execution_count": 93, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "angle30 = 30 * np.pi / 180 # angle in radians\n", "U_30 = np.array([[np.cos(angle30), np.sin(angle30)]])\n", "\n", "plot_projection(U_30, P)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Good! Remember that the dot product of a unit vector and a matrix basically performs a projection on an axis and gives us the coordinates of the resulting points on that axis." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### Matrix multiplication – Rotation\n", "Now let's create a $2 \\times 2$ matrix $V$ containing two unit vectors that make 30° and 120° angles with the horizontal axis:\n", "\n", "$V = \\begin{bmatrix} \\cos(30°) & \\sin(30°) \\\\ \\cos(120°) & \\sin(120°) \\end{bmatrix}$" ] }, { "cell_type": "code", "execution_count": 94, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[ 0.8660254, 0.5 ],\n", " [-0.5 , 0.8660254]])" ] }, "execution_count": 94, "metadata": {}, "output_type": "execute_result" } ], "source": [ "angle120 = 120 * np.pi / 180\n", "V = np.array([\n", " [np.cos(angle30), np.sin(angle30)],\n", " [np.cos(angle120), np.sin(angle120)]\n", " ])\n", "V" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Let's look at the product $VP$:" ] }, { "cell_type": "code", "execution_count": 95, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[ 2.69807621, 5.21410162, 1.8660254 , 4.23371686],\n", " [-1.32679492, 1.03108891, 1.23205081, -1.8669873 ]])" ] }, "execution_count": 95, "metadata": {}, "output_type": "execute_result" } ], "source": [ "V @ P" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The first row is equal to $V_{1,*} P$, which is the coordinates of the projection of $P$ onto the 30° axis, as we have seen above. The second row is $V_{2,*} P$, which is the coordinates of the projection of $P$ onto the 120° axis. So basically we obtained the coordinates of $P$ after rotating the horizontal and vertical axes by 30° (or equivalently after rotating the polygon by -30° around the origin)! Let's plot $VP$ to see this:" ] }, { "cell_type": "code", "execution_count": 96, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "P_rotated = V @ P\n", "plot_transformation(P, P_rotated, \"$P$\", \"$VP$\", [-2, 6, -2, 4], arrows=True)\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Matrix $V$ is called a **rotation matrix**." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### Matrix multiplication – Other linear transformations\n", "More generally, any linear transformation $f$ that maps n-dimensional vectors to m-dimensional vectors can be represented as an $m \\times n$ matrix. For example, say $\\textbf{u}$ is a 3-dimensional vector:\n", "\n", "$\\textbf{u} = \\begin{pmatrix} x \\\\ y \\\\ z \\end{pmatrix}$\n", "\n", "and $f$ is defined as:\n", "\n", "$f(\\textbf{u}) = \\begin{pmatrix}\n", "ax + by + cz \\\\\n", "dx + ey + fz\n", "\\end{pmatrix}$\n", "\n", "This transformation $f$ maps 3-dimensional vectors to 2-dimensional vectors in a linear way (i.e. the resulting coordinates only involve sums of multiples of the original coordinates). We can represent this transformation as matrix $F$:\n", "\n", "$F = \\begin{bmatrix}\n", "a & b & c \\\\\n", "d & e & f\n", "\\end{bmatrix}$\n", "\n", "Now, to compute $f(\\textbf{u})$ we can simply do a matrix multiplication:\n", "\n", "$f(\\textbf{u}) = F \\textbf{u}$\n", "\n", "If we have a matrix $G = \\begin{bmatrix}\\textbf{u}_1 & \\textbf{u}_2 & \\cdots & \\textbf{u}_q \\end{bmatrix}$, where each $\\textbf{u}_i$ is a 3-dimensional column vector, then $FG$ results in the linear transformation of all vectors $\\textbf{u}_i$ as defined by the matrix $F$:\n", "\n", "$FG = \\begin{bmatrix}f(\\textbf{u}_1) & f(\\textbf{u}_2) & \\cdots & f(\\textbf{u}_q) \\end{bmatrix}$\n", "\n", "To summarize, the matrix on the left-hand side of a dot product specifies what linear transformation to apply to the right-hand side vectors. We have already shown that this can be used to perform projections and rotations, but any other linear transformation is possible. For example, here is a transformation known as a *shear mapping*:" ] }, { "cell_type": "code", "execution_count": 97, "metadata": { "scrolled": true }, "outputs": [ { "data": { "image/png": "iVBORw0KGgoAAAANSUhEUgAAAVgAAAD8CAYAAAAylrwMAAAAOXRFWHRTb2Z0d2FyZQBNYXRwbG90bGliIHZlcnNpb24zLjQuMywgaHR0cHM6Ly9tYXRwbG90bGliLm9yZy/MnkTPAAAACXBIWXMAAAsTAAALEwEAmpwYAAAtoUlEQVR4nO3deXzddZ3v8df3LNmTpkvapk2XdEnoQkv30lJI2ZEdFIqioo7VUbk4chX0XnV0hoczjoPiqHfEDR0RpwJVLMoylrBTaLrTku5LuqRb0uw52/f+8ekhS9PmnPT8zvp5Ph55pE3O8v2lp+98znc11lqUUkrFnivRDVBKqXSlAauUUg7RgFVKKYdowCqllEM0YJVSyiEasEop5ZB+A9YYU2mM2dDto8kY88U4tE0ppVKaiWYerDHGDRwEFlhr9znWKqWUSgPRdhFcAezScFVKqf55orz9MuCJvr5hjFkOLAfIycmZM3bs2PNsWuoJhUK4XJnXra3XnVky9bq3b99+3FpbEs19Iu4iMMZkAYeAadba+nPdtrKy0tbW1kbTjrRQXV1NVVVVopsRd3rdmSVTr9sYU2OtnRvNfaL5NXQdsK6/cFVKKSWiCdi7OEv3gFJKqTNFFLDGmDzgKuBpZ5ujlFLpI6JBLmttGzDU4bYopVRaybyhQKWUihMNWKWUcogGrFJKOUQDVimlHKIBq5RSDtGAVUoph2jAKqWUQzRglVLKIRqwSinlEA1YpZRyiAasUko5RANWKaUcogGrlFIO0YBVSimHaMAqpZRDNGCVUsohGrBKKeUQDVillHKIBqxSSjlEA1YppRyiAauUUg7RgFVKKYdEFLDGmGJjzJPGmPeMMduMMRc73TCllEp1nghv9wjwnLX2g8aYLCDPwTYppVRa6DdgjTFFwKXAPQDWWh/gc7ZZSimV+oy19tw3MOYi4FFgKzATqAHus9a29rrdcmA5QElJyZwVK1Y40d6k1tLSQkFBQaKbEXd63ZklU6976dKlNdbaudHcJ5KAnQu8BSy21q4xxjwCNFlrv362+1RWVtra2tpo2pEWqqurqaqqSnQz4k6vO7Nk6nUbY6IO2EgGueqAOmvtmtN/fxKYHW3jlFIq0/QbsNbaI8ABY0zl6S9dgXQXKKWUOodIZxHcCzx+egbBbuATzjVJKaXSQ0QBa63dAETV96CUUplOV3IppZRDNGCVUsohGrBKKeUQDVillHKIBqxSSjlEA1YppRyiAauUUg7RgFVKKYdowCqllEM0YJVSyiEasEop5RANWKWUcogGrFJKOUQDVimlHKIBq5RSDtGAVUoph2jAKqWUQzRglVLKIRqwSinlEA1YpZRyiAasUko5RANWKaUcEtGx3caYvUAzEAQC1lo9wlsppfoRUcCettRae9yxliilVJrRLgKllHKIsdb2fyNj9gANgAV+aq19tI/bLAeWA5SUlMxZsWJFjJua/FpaWigoKEh0M+JOrzuzZOp1L126tCba7tFIA3aUtfaQMWY48CJwr7X2lbPdvrKy0tbW1kbTjrRQXV1NVVVVopsRd3rdmSVTr9sYE3XARtRFYK09dPrzUWAlMD/65imlVGbpN2CNMfnGmMLwn4GrgS1ON0wppVJdJLMIRgArjTHh2//OWvuco61SSqk00G/AWmt3AzPj0BallEorOk1LKaUcogGrlFIO0YBVSimHaMAqpZRDNGCVUsohGrBKKeUQDVillHKIBqxSSjlEA1YppRyiAauUUg7RgFVKKYdowCqllEM0YJVSyiEasEop5RANWKWUcogGrFJKOUQDVimlHKIBq5RSDtGAVUoph2jAKqWUQzRglVLKIRqwSinlkIgD1hjjNsasN8ascrJBSimVLqKpYO8DtjnVEKWUSjcRBawxpgy4Hvi5s81RSqn0EWkF+wPgK0DIuaYopVR68fR3A2PMDcBRa22NMabqHLdbDiwHKCkpobq6OkZNTB0tLS163RlEr1v1x1hrz30DY74DfBQIADlAEfC0tfbus92nsrLS1tbWxrKdKaG6upqqqqpENyPu9LozS6ZetzGmxlo7N5r79NtFYK39qrW2zFo7HlgGrD5XuCqllBI6D1YppRzSbx9sd9baaqDakZYopVSa0QpWKaUcogGrlFIO0YBVSimHaMAqpZRDNGCVUsohGrBKKeUQDVillHKIBqxSSjlEA1YppRyiAasGrLERnn8ejhzJTnRTVKY7fhweegh27050S3qIaqmsUmGhEPzbvwfxBSxlI3MS3RyVSayVQN24UT4fOgRvvgnZ2XDsGEyYkOgWvk8DVkWssRHWrYO5Fwc41tLBkNGGo/tzGDOmLdFNU5mgthbWrIENG2DvXmhrA58Piorg0kvhrrugtDTRrexBA1b1q7ERXn0V1rwT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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "F_shear = np.array([\n", " [1, 1.5],\n", " [0, 1]\n", " ])\n", "plot_transformation(P, F_shear @ P, \"$P$\", \"$F_{shear} P$\",\n", " axis=[0, 10, 0, 7])\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Let's look at how this transformation affects the **unit square**: " ] }, { "cell_type": "code", "execution_count": 98, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "Square = np.array([\n", " [0, 0, 1, 1],\n", " [0, 1, 1, 0]\n", " ])\n", "plot_transformation(Square, F_shear @ Square, \"$Square$\", \"$F_{shear} Square$\",\n", " axis=[0, 2.6, 0, 1.8])\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Now let's look at a **squeeze mapping**:" ] }, { "cell_type": "code", "execution_count": 99, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "F_squeeze = np.array([\n", " [1.4, 0],\n", " [0, 1/1.4]\n", " ])\n", "plot_transformation(P, F_squeeze @ P, \"$P$\", \"$F_{squeeze} P$\",\n", " axis=[0, 7, 0, 5])\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The effect on the unit square is:" ] }, { "cell_type": "code", "execution_count": 100, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "plot_transformation(Square, F_squeeze @ Square, \"$Square$\", \"$F_{squeeze} Square$\",\n", " axis=[0, 1.8, 0, 1.2])\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Let's show a last one -- reflection through the horizontal axis:" ] }, { "cell_type": "code", "execution_count": 101, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "F_reflect = np.array([\n", " [1, 0],\n", " [0, -1]\n", " ])\n", "plot_transformation(P, F_reflect @ P, \"$P$\", \"$F_{reflect} P$\",\n", " axis=[-2, 9, -4.5, 4.5])\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Matrix inverse\n", "Now that we understand that a matrix can represent any linear transformation, a natural question is: can we find a transformation matrix that reverses the effect of a given transformation matrix $F$? The answer is yes… sometimes! When it exists, such a matrix is called the **inverse** of $F$, and it is noted $F^{-1}$.\n", "\n", "For example, the rotation, the shear mapping and the squeeze mapping above all have inverse transformations. Let's demonstrate this on the shear mapping:" ] }, { "cell_type": "code", "execution_count": 102, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "F_inv_shear = np.array([\n", " [1, -1.5],\n", " [0, 1]\n", "])\n", "P_sheared = F_shear @ P\n", "P_unsheared = F_inv_shear @ P_sheared\n", "plot_transformation(P_sheared, P_unsheared, \"$P_{sheared}$\", \"$P_{unsheared}$\",\n", " axis=[0, 10, 0, 7])\n", "plt.plot(P[0], P[1], \"b--\")\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "We applied a shear mapping on $P$, just like we did before, but then we applied a second transformation to the result, and *lo and behold* this had the effect of coming back to the original $P$ (I've plotted the original $P$'s outline to double-check). The second transformation is the inverse of the first one.\n", "\n", "We defined the inverse matrix $F_{shear}^{-1}$ manually this time, but NumPy provides an `inv` function to compute a matrix's inverse, so we could have written instead:" ] }, { "cell_type": "code", "execution_count": 103, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[ 1. , -1.5],\n", " [ 0. , 1. ]])" ] }, "execution_count": 103, "metadata": {}, "output_type": "execute_result" } ], "source": [ "F_inv_shear = LA.inv(F_shear)\n", "F_inv_shear" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Only square matrices can be inversed. This makes sense when you think about it: if you have a transformation that reduces the number of dimensions, then some information is lost and there is no way that you can get it back. For example say you use a $2 \\times 3$ matrix to project a 3D object onto a plane. The result may look like this:" ] }, { "cell_type": "code", "execution_count": 104, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "plt.plot([0, 0, 1, 1, 0, 0.1, 0.1, 0, 0.1, 1.1, 1.0, 1.1, 1.1, 1.0, 1.1, 0.1],\n", " [0, 1, 1, 0, 0, 0.1, 1.1, 1.0, 1.1, 1.1, 1.0, 1.1, 0.1, 0, 0.1, 0.1],\n", " \"r-\")\n", "plt.axis([-0.5, 2.1, -0.5, 1.5])\n", "plt.gca().set_aspect(\"equal\")\n", "plt.grid()\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Looking at this image, it is impossible to tell whether this is the projection of a cube or the projection of a narrow rectangular object. Some information has been lost in the projection.\n", "\n", "Even square transformation matrices can lose information. For example, consider this transformation matrix:" ] }, { "cell_type": "code", "execution_count": 105, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "F_project = np.array([\n", " [1, 0],\n", " [0, 0]\n", " ])\n", "plot_transformation(P, F_project @ P, \"$P$\", r\"$F_{project} \\cdot P$\",\n", " axis=[0, 6, -1, 4])\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "This transformation matrix performs a projection onto the horizontal axis. Our polygon gets entirely flattened out so some information is entirely lost, and it is impossible to go back to the original polygon using a linear transformation. In other words, $F_{project}$ has no inverse. Such a square matrix that cannot be inversed is called a **singular matrix** (aka degenerate matrix). If we ask NumPy to calculate its inverse, it raises an exception:" ] }, { "cell_type": "code", "execution_count": 106, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "LinAlgError: Singular matrix\n" ] } ], "source": [ "try:\n", " LA.inv(F_project)\n", "except LA.LinAlgError as e:\n", " print(\"LinAlgError:\", e)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Here is another example of a singular matrix. This one performs a projection onto the axis at a 30° angle above the horizontal axis:" ] }, { "cell_type": "code", "execution_count": 107, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "angle30 = 30 * np.pi / 180\n", "F_project_30 = np.array([\n", " [np.cos(angle30)**2, np.sin(2*angle30)/2],\n", " [np.sin(2*angle30)/2, np.sin(angle30)**2]\n", " ])\n", "plot_transformation(P, F_project_30 @ P, \"$P$\", r\"$F_{project\\_30} \\cdot P$\",\n", " axis=[0, 6, -1, 4])\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "But this time, due to floating point rounding errors, NumPy manages to calculate an inverse (notice how large the elements are, though):" ] }, { "cell_type": "code", "execution_count": 108, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[ 1.20095990e+16, -2.08012357e+16],\n", " [-2.08012357e+16, 3.60287970e+16]])" ] }, "execution_count": 108, "metadata": {}, "output_type": "execute_result" } ], "source": [ "LA.inv(F_project_30)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "As you might expect, the dot product of a matrix by its inverse results in the identity matrix:\n", "\n", "$M \\cdot M^{-1} = M^{-1} \\cdot M = I$\n", "\n", "This makes sense since doing a linear transformation followed by the inverse transformation results in no change at all." ] }, { "cell_type": "code", "execution_count": 109, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[1., 0.],\n", " [0., 1.]])" ] }, "execution_count": 109, "metadata": {}, "output_type": "execute_result" } ], "source": [ "F_shear @ LA.inv(F_shear)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Another way to express this is that the inverse of the inverse of a matrix $M$ is $M$ itself:\n", "\n", "$((M)^{-1})^{-1} = M$" ] }, { "cell_type": "code", "execution_count": 110, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[1. , 1.5],\n", " [0. , 1. ]])" ] }, "execution_count": 110, "metadata": {}, "output_type": "execute_result" } ], "source": [ "LA.inv(LA.inv(F_shear))" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Also, the inverse of scaling by a factor of $\\lambda$ is of course scaling by a factor of $\\frac{1}{\\lambda}$:\n", "\n", "$ (\\lambda \\times M)^{-1} = \\frac{1}{\\lambda} \\times M^{-1}$\n", "\n", "Once you understand the geometric interpretation of matrices as linear transformations, most of these properties seem fairly intuitive.\n", "\n", "A matrix that is its own inverse is called an **involution**. The simplest examples are reflection matrices, or a rotation by 180°, but there are also more complex involutions, for example imagine a transformation that squeezes horizontally, then reflects over the vertical axis and finally rotates by 90° clockwise. Pick up a napkin and try doing that twice: you will end up in the original position. Here is the corresponding involutory matrix:" ] }, { "cell_type": "code", "execution_count": 111, "metadata": {}, "outputs": [ { "data": { "image/png": "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OAW5lyIRWL8ejh51y+kLChTg7UnUws888+Sj7REj3OyWiy5yo82nnnKlqAsu6J1ySzzufnddvfnGnDnw7W8fH6wrVnjfrq5K1McfeACmTHEXk4uL3c1Aior8a5ekhILcC61LKDt3usUuo0drBHQyW7e6PysqOn5eMNgyuly92u17/vLLvVNuqa11F6O7sgVvLOZeqGfM8LYNJzNiBFjLmpoaqk72nMSMlZtughSsAJb0ogVByYhEKF63Dm69FX76U7di8aqr4NRT/dlSNlMkLnR2tqR5xQr45jfd501Nrnzw0ktuNJyfD3//9+574bCbtvjOOy0/G4kw5+ab4YknWh771a9g0iQ3Up079/jnr1kD06a5kez997vpkK2ddpp7od67141wm5pg1izXh7/8BZ591s2F7+xcsRj87/+6UfN3vuMuThYXwx13dOdv8ESrVrnrCwrxPkkj8p6qq4M332TgG2+0zEJRCaVzTU2u/j1rVufP3brVvSgCbNsGBw64xUPXXONG5g88AN/6lnv3U1nppjDOnOme/4tfECkpgeuuc1/ffz889JAL48pKV3e/7jp3XHBBnhhhr17dcpxEmzdtco+dcoo7zgMPwJ/+5F5E+veHH/7Q1faXLYPf/hZefBFuucW1f80at0DnuutcH959170DCIVcX66/HubNcxcje3IhvKEBNm927wSlT1KQd0eihPLmm265eSjEh1dcwZjiYr9bljkSFzo7K6uAC/Jp09zn27a5+ngirCoq3Ej4iSfcaHnUKBfkAIcPwz33sOXuu5kFbm/0u+92OzFOmuSe8+Uvw/e+52Z4DBniwjZxg4w333Sh/cor7ndurbvesWyZG2kvXequg3zxi+5FfN48ePJJV7v/yU/cYq9zz3Xhv2+fu4vSnj3u++PGuXOdfTYsWOAujE6enNzf6Zo1bqTf+h2B9CkK8q5obxrhxImQn080MQ9auqar9XFw4X311S2fX3FFy/c++siVEcaMcSH6wQfu+sR3vws/+hHMn094yBAXphs3ulLOkSPw8MPuz61b3Yj4nnvcKsgVK9yMmZdecud67jkX3Hl5LsTLy2HtWhfg+/e7F4QJE1xZpKTEBfXf/q0bva9b11L2Adeu3Fy3wjIQgP/6Lxfg8+e7C76vv+62KO7ptNREfVxB3mcpyDtTWws/+1nfXErfGy677Pjl4ydT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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "F_involution = np.array([\n", " [0, -2],\n", " [-1/2, 0]\n", " ])\n", "plot_transformation(P, F_involution @ P, \"$P$\", r\"$F_{involution} \\cdot P$\",\n", " axis=[-8, 5, -4, 4])\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Finally, a square matrix $H$ whose inverse is its own transpose is an **orthogonal matrix**:\n", "\n", "$H^{-1} = H^T$\n", "\n", "Therefore:\n", "\n", "$H \\cdot H^T = H^T \\cdot H = I$\n", "\n", "It corresponds to a transformation that preserves distances, such as rotations and reflections, and combinations of these, but not rescaling, shearing or squeezing. Let's check that $F_{reflect}$ is indeed orthogonal:" ] }, { "cell_type": "code", "execution_count": 112, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[1, 0],\n", " [0, 1]])" ] }, "execution_count": 112, "metadata": {}, "output_type": "execute_result" } ], "source": [ "F_reflect @ F_reflect.T" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Determinant\n", "The determinant of a square matrix $M$, noted $\\det(M)$ or $\\det M$ or $|M|$ is a value that can be calculated from its elements $(M_{i,j})$ using various equivalent methods. One of the simplest methods is this recursive approach:\n", "\n", "$|M| = M_{1,1}\\times|M^{(1,1)}| - M_{1,2}\\times|M^{(1,2)}| + M_{1,3}\\times|M^{(1,3)}| - M_{1,4}\\times|M^{(1,4)}| + \\cdots ± M_{1,n}\\times|M^{(1,n)}|$\n", "\n", "* Where $M^{(i,j)}$ is the matrix $M$ without row $i$ and column $j$.\n", "\n", "For example, let's calculate the determinant of the following $3 \\times 3$ matrix:\n", "\n", "$M = \\begin{bmatrix}\n", " 1 & 2 & 3 \\\\\n", " 4 & 5 & 6 \\\\\n", " 7 & 8 & 0\n", "\\end{bmatrix}$\n", "\n", "Using the method above, we get:\n", "\n", "$|M| = 1 \\times \\left | \\begin{bmatrix} 5 & 6 \\\\ 8 & 0 \\end{bmatrix} \\right |\n", " - 2 \\times \\left | \\begin{bmatrix} 4 & 6 \\\\ 7 & 0 \\end{bmatrix} \\right |\n", " + 3 \\times \\left | \\begin{bmatrix} 4 & 5 \\\\ 7 & 8 \\end{bmatrix} \\right |$\n", "\n", "Now we need to compute the determinant of each of these $2 \\times 2$ matrices (these determinants are called **minors**):\n", "\n", "$\\left | \\begin{bmatrix} 5 & 6 \\\\ 8 & 0 \\end{bmatrix} \\right | = 5 \\times 0 - 6 \\times 8 = -48$\n", "\n", "$\\left | \\begin{bmatrix} 4 & 6 \\\\ 7 & 0 \\end{bmatrix} \\right | = 4 \\times 0 - 6 \\times 7 = -42$\n", "\n", "$\\left | \\begin{bmatrix} 4 & 5 \\\\ 7 & 8 \\end{bmatrix} \\right | = 4 \\times 8 - 5 \\times 7 = -3$\n", "\n", "Now we can calculate the final result:\n", "\n", "$|M| = 1 \\times (-48) - 2 \\times (-42) + 3 \\times (-3) = 27$" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "To get the determinant of a matrix, you can call NumPy's `det` function in the `numpy.linalg` module:" ] }, { "cell_type": "code", "execution_count": 113, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "27.0" ] }, "execution_count": 113, "metadata": {}, "output_type": "execute_result" } ], "source": [ "M = np.array([\n", " [1, 2, 3],\n", " [4, 5, 6],\n", " [7, 8, 0]\n", " ])\n", "LA.det(M)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "One of the main uses of the determinant is to *determine* whether a square matrix can be inversed or not: if the determinant is equal to 0, then the matrix *cannot* be inversed (it is a singular matrix), and if the determinant is not 0, then it *can* be inversed.\n", "\n", "For example, let's compute the determinant for the $F_{project}$, $F_{project\\_30}$ and $F_{shear}$ matrices that we defined earlier:" ] }, { "cell_type": "code", "execution_count": 114, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "0.0" ] }, "execution_count": 114, "metadata": {}, "output_type": "execute_result" } ], "source": [ "LA.det(F_project)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "That's right, $F_{project}$ is singular, as we saw earlier." ] }, { "cell_type": "code", "execution_count": 115, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "2.0816681711721642e-17" ] }, "execution_count": 115, "metadata": {}, "output_type": "execute_result" } ], "source": [ "LA.det(F_project_30)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "This determinant is suspiciously close to 0: it really should be 0, but it's not due to tiny floating point errors. The matrix is actually singular." ] }, { "cell_type": "code", "execution_count": 116, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "1.0" ] }, "execution_count": 116, "metadata": {}, "output_type": "execute_result" } ], "source": [ "LA.det(F_shear)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Perfect! This matrix *can* be inversed as we saw earlier. Wow, math really works!" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The determinant can also be used to measure how much a linear transformation affects surface areas: for example, the projection matrices $F_{project}$ and $F_{project\\_30}$ completely flatten the polygon $P$, until its area is zero. This is why the determinant of these matrices is 0. The shear mapping modified the shape of the polygon, but it did not affect its surface area, which is why the determinant is 1. You can try computing the determinant of a rotation matrix, and you should also find 1. What about a scaling matrix? Let's see:" ] }, { "cell_type": "code", "execution_count": 117, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "F_scale = np.array([\n", " [0.5, 0],\n", " [0, 0.5]\n", " ])\n", "plot_transformation(P, F_scale @ P, \"$P$\", r\"$F_{scale} \\cdot P$\",\n", " axis=[0, 6, -1, 4])\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "We rescaled the polygon by a factor of 1/2 on both vertical and horizontal axes so the surface area of the resulting polygon is 1/4$^{th}$ of the original polygon. Let's compute the determinant and check that:" ] }, { "cell_type": "code", "execution_count": 118, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "0.25" ] }, "execution_count": 118, "metadata": {}, "output_type": "execute_result" } ], "source": [ "LA.det(F_scale)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Correct!\n", "\n", "The determinant can actually be negative, when the transformation results in a \"flipped over\" version of the original polygon (e.g. a left-hand glove becomes a right-hand glove). For example, the determinant of the `F_reflect` matrix is -1 because the surface area is preserved but the polygon gets flipped over:" ] }, { "cell_type": "code", "execution_count": 119, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "-1.0" ] }, "execution_count": 119, "metadata": {}, "output_type": "execute_result" } ], "source": [ "LA.det(F_reflect)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Composing linear transformations\n", "Several linear transformations can be chained simply by performing multiple dot products in a row. For example, to perform a squeeze mapping followed by a shear mapping, just write:" ] }, { "cell_type": "code", "execution_count": 120, "metadata": {}, "outputs": [], "source": [ "P_squeezed_then_sheared = F_shear @ (F_squeeze @ P)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Since the dot product is associative, the following code is equivalent:" ] }, { "cell_type": "code", "execution_count": 121, "metadata": {}, "outputs": [], "source": [ "P_squeezed_then_sheared = F_shear @ F_squeeze @ P" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Note that the order of the transformations is the reverse of the dot product order.\n", "\n", "If we are going to perform this composition of linear transformations more than once, we might as well save the composition matrix like this:" ] }, { "cell_type": "code", "execution_count": 122, "metadata": {}, "outputs": [], "source": [ "F_squeeze_then_shear = F_shear @ F_squeeze\n", "P_squeezed_then_sheared = F_squeeze_then_shear @ P" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "From now on we can perform both transformations in just one dot product, which can lead to a very significant performance boost." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "What if you want to perform the inverse of this double transformation? Well, if you squeezed and then you sheared, and you want to undo what you have done, it should be obvious that you should unshear first and then unsqueeze. In more mathematical terms, given two invertible (aka nonsingular) matrices $Q$ and $R$:\n", "\n", "$(Q \\cdot R)^{-1} = R^{-1} \\cdot Q^{-1}$\n", "\n", "And in NumPy:" ] }, { "cell_type": "code", "execution_count": 123, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[ True, True],\n", " [ True, True]])" ] }, "execution_count": 123, "metadata": {}, "output_type": "execute_result" } ], "source": [ "LA.inv(F_shear @ F_squeeze) == LA.inv(F_squeeze) @ LA.inv(F_shear)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Singular Value Decomposition\n", "It turns out that any $m \\times n$ matrix $M$ can be decomposed into the dot product of three simple matrices:\n", "* a rotation matrix $U$ (an $m \\times m$ orthogonal matrix)\n", "* a scaling & projecting matrix $\\Sigma$ (an $m \\times n$ diagonal matrix)\n", "* and another rotation matrix $V^T$ (an $n \\times n$ orthogonal matrix)\n", "\n", "$M = U \\cdot \\Sigma \\cdot V^{T}$\n", "\n", "For example, let's decompose the shear transformation:" ] }, { "cell_type": "code", "execution_count": 124, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[ 0.89442719, -0.4472136 ],\n", " [ 0.4472136 , 0.89442719]])" ] }, "execution_count": 124, "metadata": {}, "output_type": "execute_result" } ], "source": [ "U, S_diag, V_T = LA.svd(F_shear) # note: in python 3 you can rename S_diag to Σ_diag\n", "U" ] }, { "cell_type": "code", "execution_count": 125, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([2. , 0.5])" ] }, "execution_count": 125, "metadata": {}, "output_type": "execute_result" } ], "source": [ "S_diag" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Note that this is just a 1D array containing the diagonal values of Σ. To get the actual matrix Σ, we can use NumPy's `diag` function:" ] }, { "cell_type": "code", "execution_count": 126, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[2. , 0. ],\n", " [0. , 0.5]])" ] }, "execution_count": 126, "metadata": {}, "output_type": "execute_result" } ], "source": [ "S = np.diag(S_diag)\n", "S" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Now let's check that $U \\cdot \\Sigma \\cdot V^T$ is indeed equal to `F_shear`:" ] }, { "cell_type": "code", "execution_count": 127, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[ 1.00000000e+00, 1.50000000e+00],\n", " [-1.25949234e-17, 1.00000000e+00]])" ] }, "execution_count": 127, "metadata": {}, "output_type": "execute_result" } ], "source": [ "U @ np.diag(S_diag) @ V_T" ] }, { "cell_type": "code", "execution_count": 128, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[1. , 1.5],\n", " [0. , 1. ]])" ] }, "execution_count": 128, "metadata": {}, "output_type": "execute_result" } ], "source": [ "F_shear" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "It worked like a charm. Let's apply these transformations one by one (in reverse order) on the unit square to understand what's going on. First, let's apply the first rotation $V^T$:" ] }, { "cell_type": "code", "execution_count": 129, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "plot_transformation(Square, V_T @ Square, \"$Square$\", r\"$V^T \\cdot Square$\",\n", " axis=[-0.5, 3.5 , -1.5, 1.5])\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Now let's rescale along the vertical and horizontal axes using $\\Sigma$:" ] }, { "cell_type": "code", "execution_count": 130, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "plot_transformation(V_T @ Square, S @ V_T @ Square,\n", " r\"$V^T \\cdot Square$\",\n", " r\"$\\Sigma \\cdot V^T \\cdot Square$\",\n", " axis=[-0.5, 3.5 , -1.5, 1.5])\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Finally, we apply the second rotation $U$:" ] }, { "cell_type": "code", "execution_count": 131, "metadata": {}, "outputs": [ { "data": { "image/png": "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\n", "text/plain": [ "
" ] }, "metadata": { "needs_background": "light" }, "output_type": "display_data" } ], "source": [ "plot_transformation(S @ V_T @ Square, U @ S @ V_T @ Square,\n", " r\"$\\Sigma \\cdot V^T \\cdot Square$\",\n", " r\"$U \\cdot \\Sigma \\cdot V^T \\cdot Square$\",\n", " axis=[-0.5, 3.5 , -1.5, 1.5])\n", "plt.show()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "And we can see that the result is indeed a shear mapping of the original unit square." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Eigenvectors and eigenvalues\n", "An **eigenvector** of a square matrix $M$ (also called a **characteristic vector**) is a non-zero vector that remains on the same line after transformation by the linear transformation associated with $M$. A more formal definition is any vector $v$ such that:\n", "\n", "$M \\cdot v = \\lambda \\times v$\n", "\n", "Where $\\lambda$ is a scalar value called the **eigenvalue** associated to the vector $v$.\n", "\n", "For example, any horizontal vector remains horizontal after applying the shear mapping (as you can see on the image above), so it is an eigenvector of $M$. A vertical vector ends up tilted to the right, so vertical vectors are *NOT* eigenvectors of $M$.\n", "\n", "If we look at the squeeze mapping, we find that any horizontal or vertical vector keeps its direction (although its length changes), so all horizontal and vertical vectors are eigenvectors of $F_{squeeze}$.\n", "\n", "However, rotation matrices have no eigenvectors at all (except if the rotation angle is 0° or 180°, in which case all non-zero vectors are eigenvectors).\n", "\n", "NumPy's `eig` function returns the list of unit eigenvectors and their corresponding eigenvalues for any square matrix. Let's look at the eigenvectors and eigenvalues of the squeeze mapping matrix $F_{squeeze}$:" ] }, { "cell_type": "code", "execution_count": 132, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([1.4 , 0.71428571])" ] }, "execution_count": 132, "metadata": {}, "output_type": "execute_result" } ], "source": [ "eigenvalues, eigenvectors = LA.eig(F_squeeze)\n", "eigenvalues # [λ0, λ1, …]" ] }, { "cell_type": "code", "execution_count": 133, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[1., 0.],\n", " [0., 1.]])" ] }, "execution_count": 133, "metadata": {}, "output_type": "execute_result" } ], "source": [ "eigenvectors # [v0, v1, …]" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Indeed, the horizontal vectors are stretched by a factor of 1.4, and the vertical vectors are shrunk by a factor of 1/1.4=0.714…, so far so good. Let's look at the shear mapping matrix $F_{shear}$:" ] }, { "cell_type": "code", "execution_count": 134, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([1., 1.])" ] }, "execution_count": 134, "metadata": {}, "output_type": "execute_result" } ], "source": [ "eigenvalues2, eigenvectors2 = LA.eig(F_shear)\n", "eigenvalues2 # [λ0, λ1, …]" ] }, { "cell_type": "code", "execution_count": 135, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([[ 1.00000000e+00, -1.00000000e+00],\n", " [ 0.00000000e+00, 1.48029737e-16]])" ] }, "execution_count": 135, "metadata": {}, "output_type": "execute_result" } ], "source": [ "eigenvectors2 # [v0, v1, …]" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Wait, what!? We expected just one unit eigenvector, not two. The second vector is almost equal to $\\begin{pmatrix}-1 \\\\ 0 \\end{pmatrix}$, which is on the same line as the first vector $\\begin{pmatrix}1 \\\\ 0 \\end{pmatrix}$. This is due to floating point errors. We can safely ignore vectors that are (almost) collinear (i.e. on the same line)." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Trace\n", "The trace of a square matrix $M$, noted $tr(M)$ is the sum of the values on its main diagonal. For example:" ] }, { "cell_type": "code", "execution_count": 136, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "123" ] }, "execution_count": 136, "metadata": {}, "output_type": "execute_result" } ], "source": [ "D = np.array([\n", " [100, 200, 300],\n", " [ 10, 20, 30],\n", " [ 1, 2, 3],\n", " ])\n", "D.trace()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The trace does not have a simple geometric interpretation (in general), but it has a number of properties that make it useful in many areas:\n", "* $tr(A + B) = tr(A) + tr(B)$\n", "* $tr(A \\cdot B) = tr(B \\cdot A)$\n", "* $tr(A \\cdot B \\cdot \\cdots \\cdot Y \\cdot Z) = tr(Z \\cdot A \\cdot B \\cdot \\cdots \\cdot Y)$\n", "* $tr(A^T \\cdot B) = tr(A \\cdot B^T) = tr(B^T \\cdot A) = tr(B \\cdot A^T) = \\sum_{i,j}X_{i,j} \\times Y_{i,j}$\n", "* …\n", "\n", "It does, however, have a useful geometric interpretation in the case of projection matrices (such as $F_{project}$ that we discussed earlier): it corresponds to the number of dimensions after projection. For example:" ] }, { "cell_type": "code", "execution_count": 137, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "1" ] }, "execution_count": 137, "metadata": {}, "output_type": "execute_result" } ], "source": [ "F_project.trace()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "# What's next?\n", "This concludes this introduction to Linear Algebra. Although these basics cover most of what you will need to know for Machine Learning, if you wish to go deeper into this topic there are many options available: Linear Algebra [books](https://linear.axler.net/), [Khan Academy](https://www.khanacademy.org/math/linear-algebra) lessons, or just [Wikipedia](https://en.wikipedia.org/wiki/Linear_algebra) pages." ] } ], "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.8.12" }, "toc": { "toc_cell": false, "toc_number_sections": true, "toc_threshold": 6, "toc_window_display": false } }, "nbformat": 4, "nbformat_minor": 4 }