{ "cells": [ { "cell_type": "markdown", "metadata": {}, "source": [ "# Linear Algebra" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Original Tutorial may be found [here](http://wiki.scipy.org/Tentative_NumPy_Tutorial)." ] }, { "cell_type": "code", "execution_count": 1, "metadata": { "collapsed": true }, "outputs": [], "source": [ "import numpy as np" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "This Tutorial will use also the Linear Algebra (`linalg`) sub-module (sitting inside `numpy`).\n", "\n", "Refer to the [](http://docs.scipy.org/doc/numpy/reference/routines.linalg.html) for full `numpy.linalg` utilities." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Simple Array Operations" ] }, { "cell_type": "code", "execution_count": 2, "metadata": { "collapsed": true }, "outputs": [], "source": [ "a = np.array([[1.0, 2.0],\n", " [3.0, 4.0]])" ] }, { "cell_type": "code", "execution_count": 3, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([[ 1., 2.],\n", " [ 3., 4.]])" ] }, "execution_count": 3, "metadata": {}, "output_type": "execute_result" } ], "source": [ "a" ] }, { "cell_type": "code", "execution_count": 4, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([[ 1., 3.],\n", " [ 2., 4.]])" ] }, "execution_count": 4, "metadata": {}, "output_type": "execute_result" } ], "source": [ "a.transpose()" ] }, { "cell_type": "code", "execution_count": 5, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([[ 1., 2.],\n", " [ 3., 4.]])" ] }, "execution_count": 5, "metadata": {}, "output_type": "execute_result" } ], "source": [ "a" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Compute the inverse. This [MathIsFun.com](http://www.mathsisfun.com/algebra/matrix-inverse.html) article provides some excellent examples in explaining inverse of a matrix." ] }, { "cell_type": "code", "execution_count": 6, "metadata": { "collapsed": false }, "outputs": [], "source": [ "a_inv = np.linalg.inv(a)" ] }, { "cell_type": "code", "execution_count": 7, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([[-2. , 1. ],\n", " [ 1.5, -0.5]])" ] }, "execution_count": 7, "metadata": {}, "output_type": "execute_result" } ], "source": [ "a_inv" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "We know that, multiplying (dot multiplication) a matrix and its inverse gives us an identify matrix (see the MathIsFun.com website!)." ] }, { "cell_type": "code", "execution_count": 8, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([[ 1.00000000e+00, 1.11022302e-16],\n", " [ 0.00000000e+00, 1.00000000e+00]])" ] }, "execution_count": 8, "metadata": {}, "output_type": "execute_result" } ], "source": [ "np.dot(a, a_inv)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "See? :)" ] }, { "cell_type": "code", "execution_count": 9, "metadata": { "collapsed": false }, "outputs": [], "source": [ "u = np.eye(2) # unit 2x2 matrix; \"eye\" represents \"I\" (Identify Matrix)" ] }, { "cell_type": "code", "execution_count": 10, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([[ 1., 0.],\n", " [ 0., 1.]])" ] }, "execution_count": 10, "metadata": {}, "output_type": "execute_result" } ], "source": [ "u" ] }, { "cell_type": "code", "execution_count": 11, "metadata": { "collapsed": true }, "outputs": [], "source": [ "j = np.array([[0.0, -1.0],\n", " [1.0, 0.0]])" ] }, { "cell_type": "code", "execution_count": 12, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([[ 0., -1.],\n", " [ 1., 0.]])" ] }, "execution_count": 12, "metadata": {}, "output_type": "execute_result" } ], "source": [ "j" ] }, { "cell_type": "code", "execution_count": 13, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([[-1., 0.],\n", " [ 0., -1.]])" ] }, "execution_count": 13, "metadata": {}, "output_type": "execute_result" } ], "source": [ "np.dot(j, j) # matrix product" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Use the `trace()` function to return the sum along the diagonals of the array. See [this NumPy Doc](http://docs.scipy.org/doc/numpy/reference/generated/numpy.trace.html#numpy.trace). " ] }, { "cell_type": "code", "execution_count": 14, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "2.0" ] }, "execution_count": 14, "metadata": {}, "output_type": "execute_result" } ], "source": [ "np.trace(u) # trace" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Say we have three matrices:\n", "\n", "```\n", "ax = y\n", "```\n", "\n", "in which `a` and `y` are known.\n", "\n", "We want to solve `x`." ] }, { "cell_type": "code", "execution_count": 15, "metadata": { "collapsed": true }, "outputs": [], "source": [ "a = np.array([[1.0, 2.0],\n", " [3.0, 4.0]])" ] }, { "cell_type": "code", "execution_count": 16, "metadata": { "collapsed": true }, "outputs": [], "source": [ "y = np.array([[5.], [7.]])" ] }, { "cell_type": "code", "execution_count": 17, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([[ 1., 2.],\n", " [ 3., 4.]])" ] }, "execution_count": 17, "metadata": {}, "output_type": "execute_result" } ], "source": [ "a" ] }, { "cell_type": "code", "execution_count": 18, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([[ 5.],\n", " [ 7.]])" ] }, "execution_count": 18, "metadata": {}, "output_type": "execute_result" } ], "source": [ "y" ] }, { "cell_type": "code", "execution_count": 19, "metadata": { "collapsed": false }, "outputs": [], "source": [ "x = np.linalg.solve(a, y)" ] }, { "cell_type": "code", "execution_count": 20, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([[-3.],\n", " [ 4.]])" ] }, "execution_count": 20, "metadata": {}, "output_type": "execute_result" } ], "source": [ "x" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "To prove that this is correct, this must be true:\n", "\n", "```\n", "ax = y\n", "```" ] }, { "cell_type": "code", "execution_count": 21, "metadata": { "collapsed": false }, "outputs": [], "source": [ "s = (np.dot(a,x) == y)" ] }, { "cell_type": "code", "execution_count": 22, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([[ True],\n", " [ True]], dtype=bool)" ] }, "execution_count": 22, "metadata": {}, "output_type": "execute_result" } ], "source": [ "s" ] }, { "cell_type": "code", "execution_count": 23, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "True" ] }, "execution_count": 23, "metadata": {}, "output_type": "execute_result" } ], "source": [ "s.all()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Or just visualize it:" ] }, { "cell_type": "code", "execution_count": 24, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([[ 5.],\n", " [ 7.]])" ] }, "execution_count": 24, "metadata": {}, "output_type": "execute_result" } ], "source": [ "np.dot(a,x)" ] }, { "cell_type": "code", "execution_count": 25, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([[ 5.],\n", " [ 7.]])" ] }, "execution_count": 25, "metadata": {}, "output_type": "execute_result" } ], "source": [ "y" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "It certain looks like:\n", "\n", "```\n", "ax = y\n", "```" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Now, eigenvalue..." ] }, { "cell_type": "code", "execution_count": 26, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([[ 0., -1.],\n", " [ 1., 0.]])" ] }, "execution_count": 26, "metadata": {}, "output_type": "execute_result" } ], "source": [ "j" ] }, { "cell_type": "code", "execution_count": 27, "metadata": { "collapsed": false, "scrolled": true }, "outputs": [ { "data": { "text/plain": [ "(array([ 0.+1.j, 0.-1.j]),\n", " array([[ 0.70710678+0.j , 0.70710678-0.j ],\n", " [ 0.00000000-0.70710678j, 0.00000000+0.70710678j]]))" ] }, "execution_count": 27, "metadata": {}, "output_type": "execute_result" } ], "source": [ "np.linalg.eig(j)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "See [this article](http://www.sosmath.com/matrix/eigen0/eigen0.html) to learn more about eigenvalue and eigenvector." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Matrix Class" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Here is a short intro to the Matrix class." ] }, { "cell_type": "code", "execution_count": 28, "metadata": { "collapsed": false }, "outputs": [], "source": [ "A = np.matrix('1.0 2.0; 3.0 4.0')" ] }, { "cell_type": "code", "execution_count": 29, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "matrix([[ 1., 2.],\n", " [ 3., 4.]])" ] }, "execution_count": 29, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A" ] }, { "cell_type": "code", "execution_count": 30, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "numpy.matrixlib.defmatrix.matrix" ] }, "execution_count": 30, "metadata": {}, "output_type": "execute_result" } ], "source": [ "type(A)" ] }, { "cell_type": "code", "execution_count": 31, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "matrix([[ 1., 2.],\n", " [ 3., 4.]])" ] }, "execution_count": 31, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A" ] }, { "cell_type": "code", "execution_count": 32, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "matrix([[ 1., 3.],\n", " [ 2., 4.]])" ] }, "execution_count": 32, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A.T # Transpose" ] }, { "cell_type": "code", "execution_count": 33, "metadata": { "collapsed": false }, "outputs": [], "source": [ "X = np.matrix('5.0 7.0')" ] }, { "cell_type": "code", "execution_count": 34, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "matrix([[ 5., 7.]])" ] }, "execution_count": 34, "metadata": {}, "output_type": "execute_result" } ], "source": [ "X" ] }, { "cell_type": "code", "execution_count": 35, "metadata": { "collapsed": true }, "outputs": [], "source": [ "Y = X.T" ] }, { "cell_type": "code", "execution_count": 36, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "matrix([[ 5.],\n", " [ 7.]])" ] }, "execution_count": 36, "metadata": {}, "output_type": "execute_result" } ], "source": [ "Y" ] }, { "cell_type": "code", "execution_count": 37, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "matrix([[ 19.],\n", " [ 43.]])" ] }, "execution_count": 37, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A*Y # matrix multiplication" ] }, { "cell_type": "code", "execution_count": 38, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "matrix([[-2. , 1. ],\n", " [ 1.5, -0.5]])" ] }, "execution_count": 38, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A.I # inverse" ] }, { "cell_type": "code", "execution_count": 39, "metadata": { "collapsed": false, "scrolled": false }, "outputs": [ { "data": { "text/plain": [ "matrix([[-3.],\n", " [ 4.]])" ] }, "execution_count": 39, "metadata": {}, "output_type": "execute_result" } ], "source": [ "np.linalg.solve(A,Y) # solving linear equation" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Indexing: Comparing Matrices and 2D Arrays" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Note that there are some important differences between NumPy arrays and\n", "matrices. NumPy provides two fundamental objects: an N-dimensional array object\n", "and a universal function object. Other objects are built on top of these. In\n", "particular, matrices are 2-dimensional array objects that inherit from the NumPy\n", "array object. For both arrays and matrices, indices must consist of a proper\n", "combination of one or more of the following: integer scalars, ellipses, a list of integers or boolean values, a tuple of integers or boolean values, and a\n", "1-dimensional array of integer or boolean values. A matrix can be used as an index for matrices, but commonly an array, list, or other form is needed to accomplish a given task.\n", "\n", "As usual in Python, indexing is zero-based. Traditionally we represent a 2D array or matrix as a rectangular array of rows and columns, where movement along axis 0 is movement across rows, while movement along axis 1 is movement across\n", "columns.\n", "\n", "Let's make an array and matrix to slice: " ] }, { "cell_type": "code", "execution_count": 40, "metadata": { "collapsed": true }, "outputs": [], "source": [ "A = np.arange(12)" ] }, { "cell_type": "code", "execution_count": 41, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([ 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11])" ] }, "execution_count": 41, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A" ] }, { "cell_type": "code", "execution_count": 42, "metadata": { "collapsed": true }, "outputs": [], "source": [ "A.shape = (3,4)" ] }, { "cell_type": "code", "execution_count": 43, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([[ 0, 1, 2, 3],\n", " [ 4, 5, 6, 7],\n", " [ 8, 9, 10, 11]])" ] }, "execution_count": 43, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A" ] }, { "cell_type": "code", "execution_count": 44, "metadata": { "collapsed": true }, "outputs": [], "source": [ "M = np.mat(A.copy()) # np.mat Interpret the input as a matrix." ] }, { "cell_type": "code", "execution_count": 45, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "matrix([[ 0, 1, 2, 3],\n", " [ 4, 5, 6, 7],\n", " [ 8, 9, 10, 11]])" ] }, "execution_count": 45, "metadata": {}, "output_type": "execute_result" } ], "source": [ "M" ] }, { "cell_type": "code", "execution_count": 46, "metadata": { "collapsed": false }, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ " \n" ] } ], "source": [ "print type(A),\" \",type(M)" ] }, { "cell_type": "code", "execution_count": 47, "metadata": { "collapsed": false }, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "[[ 0 1 2 3]\n", " [ 4 5 6 7]\n", " [ 8 9 10 11]]\n" ] } ], "source": [ "print A" ] }, { "cell_type": "code", "execution_count": 48, "metadata": { "collapsed": false }, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "[[ 0 1 2 3]\n", " [ 4 5 6 7]\n", " [ 8 9 10 11]]\n" ] } ], "source": [ "print M" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Now, let's take some simple slices. Basic slicing uses slice objects or integers.\n", "\n", "For example, the evaluation of `A[:]` and `M[:]` will appear familiar from Python indexing, however it is important to note that slicing NumPy arrays does *not* make a copy of the data; slicing provides a new view of the same data. " ] }, { "cell_type": "code", "execution_count": 49, "metadata": { "collapsed": false }, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "[[ 0 1 2 3]\n", " [ 4 5 6 7]\n", " [ 8 9 10 11]]\n", "(3L, 4L)\n" ] } ], "source": [ "print A[:]; print A[:].shape" ] }, { "cell_type": "code", "execution_count": 50, "metadata": { "collapsed": false }, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "[[ 0 1 2 3]\n", " [ 4 5 6 7]\n", " [ 8 9 10 11]]\n", "(3L, 4L)\n" ] } ], "source": [ "print M[:]; print M[:].shape" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Now for something that differs from Python indexing: you may use commaseparated\n", "indices to index along multiple axes at the same time." ] }, { "cell_type": "code", "execution_count": 51, "metadata": { "collapsed": false }, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "[1 5 9]\n", "(3L,)\n" ] } ], "source": [ "print A[:,1]; print A[:,1].shape" ] }, { "cell_type": "code", "execution_count": 52, "metadata": { "collapsed": false }, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "[[1]\n", " [5]\n", " [9]]\n", "(3L, 1L)\n" ] } ], "source": [ "print M[:,1]; print M[:,1].shape" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Notice the difference in the last two results.\n", "\n", "Use of a single colon for the 2D array produces a 1-dimensional array, while for a matrix it produces a 2-dimensional matrix. A slice of a matrix will always produce a matrix. \n", "\n", "For example, a slice `M[2,:]` produces a matrix of shape `(1,4)`. \n", "\n", "In contrast, a slice of an array will always produce an array of the lowest possible dimension. \n", "\n", "For example, if `C` were a 3-dimensional array, `C[...,1]` produces a 2D array while C[1,:,1] produces a 1-dimensional array.\n", "\n", "From this point on, we will show results only for the array slice if the results for the corresponding matrix slice are identical.\n", "\n", "Lets say that we wanted the 1st and 3rd column of an array. One way is to slice\n", "using a list: " ] }, { "cell_type": "code", "execution_count": 53, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([[ 0, 1, 2, 3],\n", " [ 4, 5, 6, 7],\n", " [ 8, 9, 10, 11]])" ] }, "execution_count": 53, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A" ] }, { "cell_type": "code", "execution_count": 54, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([[ 1, 3],\n", " [ 5, 7],\n", " [ 9, 11]])" ] }, "execution_count": 54, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A[:,[1,3]]" ] }, { "cell_type": "code", "execution_count": 55, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([[ 1, 3],\n", " [ 5, 7],\n", " [ 9, 11]])" ] }, "execution_count": 55, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A[:,].take([1,3],axis=1)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "If we wanted to skip the first row, we could use:" ] }, { "cell_type": "code", "execution_count": 56, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([[ 5, 7],\n", " [ 9, 11]])" ] }, "execution_count": 56, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A[1:,].take([1,3],axis=1)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Or we could simply use `A[1:,[1,3]]`. Yet another way to slice the above is to use a cross product: " ] }, { "cell_type": "code", "execution_count": 57, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([[ 5, 7],\n", " [ 9, 11]])" ] }, "execution_count": 57, "metadata": {}, "output_type": "execute_result" } ], "source": [ " A[1:,[1,3]]" ] }, { "cell_type": "code", "execution_count": 58, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([[ 0, 1, 2, 3],\n", " [ 4, 5, 6, 7],\n", " [ 8, 9, 10, 11]])" ] }, "execution_count": 58, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Now let's do something a bit more complicated. Lets say that we want to retain all columns where the first row is greater than 1. One way is to create a boolean index: " ] }, { "cell_type": "code", "execution_count": 59, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([False, False, True, True], dtype=bool)" ] }, "execution_count": 59, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A[0,:] > 1" ] }, { "cell_type": "code", "execution_count": 60, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([[ 2, 3],\n", " [ 6, 7],\n", " [10, 11]])" ] }, "execution_count": 60, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A[:, A[0,:] > 1]" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Just what we wanted! But indexing the matrix is not so convenient. " ] }, { "cell_type": "code", "execution_count": 61, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "matrix([[ 0, 1, 2, 3],\n", " [ 4, 5, 6, 7],\n", " [ 8, 9, 10, 11]])" ] }, "execution_count": 61, "metadata": {}, "output_type": "execute_result" } ], "source": [ "M" ] }, { "cell_type": "code", "execution_count": 62, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "matrix([[False, False, True, True]], dtype=bool)" ] }, "execution_count": 62, "metadata": {}, "output_type": "execute_result" } ], "source": [ "M[0,:] > 1" ] }, { "cell_type": "code", "execution_count": 63, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "matrix([[ 2, 3],\n", " [ 6, 7],\n", " [10, 11]])" ] }, "execution_count": 63, "metadata": {}, "output_type": "execute_result" } ], "source": [ "M[:, M.A[0,:]>1] # Note the M.A" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "If we wanted to conditionally slice the matrix in two directions, we must adjust our strategy slightly. Instead of:" ] }, { "cell_type": "code", "execution_count": 64, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([ 6, 11])" ] }, "execution_count": 64, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A[A[:,0]>2,A[0,:]>1]" ] }, { "cell_type": "code", "execution_count": 65, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "matrix([[ 6, 11]])" ] }, "execution_count": 65, "metadata": {}, "output_type": "execute_result" } ], "source": [ "M[M.A[:,0]>2,M.A[0,:]>1]" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "we need to use the cross product `ix_()`:" ] }, { "cell_type": "code", "execution_count": 66, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "array([[ 6, 7],\n", " [10, 11]])" ] }, "execution_count": 66, "metadata": {}, "output_type": "execute_result" } ], "source": [ "A[np.ix_(A[:,0]>2,A[0,:]>1)]" ] }, { "cell_type": "code", "execution_count": 67, "metadata": { "collapsed": false }, "outputs": [ { "data": { "text/plain": [ "matrix([[ 6, 7],\n", " [10, 11]])" ] }, "execution_count": 67, "metadata": {}, "output_type": "execute_result" } ], "source": [ "M[np.ix_(M.A[:,0]>2,M.A[0,:]>1)]" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "# Conclusion" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "We have now completed lesson 7 - Linear Algebra." ] } ], "metadata": { "kernelspec": { "display_name": "Python 2", "language": "python", "name": "python2" }, "language_info": { "codemirror_mode": { "name": "ipython", "version": 2 }, "file_extension": ".py", "mimetype": "text/x-python", "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython2", "version": "2.7.9" } }, "nbformat": 4, "nbformat_minor": 0 }