# Diagonizing matrices in python
This shows you a couple of ways to find eigenvalues and eigenvectors of matrices in python.  The first method is numerical and the second method is analytical.

## Numerical eigenvalues/eigenvectors
Using the `numpy` library.


```python
import numpy as np # import the numpy numerical calculation library
```


```python
#define our matrix below.
matrix = np.array([[1.,2.,3.],[4.,5.,6.],[7.,8.,9.]])
```


```python
print(matrix)
```

    [[1. 2. 3.]
     [4. 5. 6.]
     [7. 8. 9.]]


The numpy library function to calculate eigenvalues and eigenvectors is called `np.linalg.eig()`.


```python
# calculate the eigenvalues and eigenvectors of matrix
eigenvalues, eigenvectors = np.linalg.eig(matrix)
```


```python
print(eigenvalues)
```

    [ 1.61168440e+01 -1.11684397e+00 -9.75918483e-16]



```python
# note that each column is one eigenvector
print(eigenvectors)
```

    [[-0.23197069 -0.78583024  0.40824829]
     [-0.52532209 -0.08675134 -0.81649658]
     [-0.8186735   0.61232756  0.40824829]]



```python
help(np.linalg.eig)
```

    Help on function eig in module numpy.linalg.linalg:
    
    eig(a)
        Compute the eigenvalues and right eigenvectors of a square array.
        
        Parameters
        ----------
        a : (..., M, M) array
            Matrices for which the eigenvalues and right eigenvectors will
            be computed
        
        Returns
        -------
        w : (..., M) array
            The eigenvalues, each repeated according to its multiplicity.
            The eigenvalues are not necessarily ordered. The resulting
            array will be of complex type, unless the imaginary part is
            zero in which case it will be cast to a real type. When `a`
            is real the resulting eigenvalues will be real (0 imaginary
            part) or occur in conjugate pairs
        
        v : (..., M, M) array
            The normalized (unit "length") eigenvectors, such that the
            column ``v[:,i]`` is the eigenvector corresponding to the
            eigenvalue ``w[i]``.
        
        Raises
        ------
        LinAlgError
            If the eigenvalue computation does not converge.
        
        See Also
        --------
        eigvals : eigenvalues of a non-symmetric array.
        
        eigh : eigenvalues and eigenvectors of a symmetric or Hermitian
               (conjugate symmetric) array.
        
        eigvalsh : eigenvalues of a symmetric or Hermitian (conjugate symmetric)
                   array.
        
        Notes
        -----
        
        .. versionadded:: 1.8.0
        
        Broadcasting rules apply, see the `numpy.linalg` documentation for
        details.
        
        This is implemented using the _geev LAPACK routines which compute
        the eigenvalues and eigenvectors of general square arrays.
        
        The number `w` is an eigenvalue of `a` if there exists a vector
        `v` such that ``dot(a,v) = w * v``. Thus, the arrays `a`, `w`, and
        `v` satisfy the equations ``dot(a[:,:], v[:,i]) = w[i] * v[:,i]``
        for :math:`i \in \{0,...,M-1\}`.
        
        The array `v` of eigenvectors may not be of maximum rank, that is, some
        of the columns may be linearly dependent, although round-off error may
        obscure that fact. If the eigenvalues are all different, then theoretically
        the eigenvectors are linearly independent. Likewise, the (complex-valued)
        matrix of eigenvectors `v` is unitary if the matrix `a` is normal, i.e.,
        if ``dot(a, a.H) = dot(a.H, a)``, where `a.H` denotes the conjugate
        transpose of `a`.
        
        Finally, it is emphasized that `v` consists of the *right* (as in
        right-hand side) eigenvectors of `a`.  A vector `y` satisfying
        ``dot(y.T, a) = z * y.T`` for some number `z` is called a *left*
        eigenvector of `a`, and, in general, the left and right eigenvectors
        of a matrix are not necessarily the (perhaps conjugate) transposes
        of each other.
        
        References
        ----------
        G. Strang, *Linear Algebra and Its Applications*, 2nd Ed., Orlando, FL,
        Academic Press, Inc., 1980, Various pp.
        
        Examples
        --------
        >>> from numpy import linalg as LA
        
        (Almost) trivial example with real e-values and e-vectors.
        
        >>> w, v = LA.eig(np.diag((1, 2, 3)))
        >>> w; v
        array([ 1.,  2.,  3.])
        array([[ 1.,  0.,  0.],
               [ 0.,  1.,  0.],
               [ 0.,  0.,  1.]])
        
        Real matrix possessing complex e-values and e-vectors; note that the
        e-values are complex conjugates of each other.
        
        >>> w, v = LA.eig(np.array([[1, -1], [1, 1]]))
        >>> w; v
        array([ 1. + 1.j,  1. - 1.j])
        array([[ 0.70710678+0.j        ,  0.70710678+0.j        ],
               [ 0.00000000-0.70710678j,  0.00000000+0.70710678j]])
        
        Complex-valued matrix with real e-values (but complex-valued e-vectors);
        note that a.conj().T = a, i.e., a is Hermitian.
        
        >>> a = np.array([[1, 1j], [-1j, 1]])
        >>> w, v = LA.eig(a)
        >>> w; v
        array([  2.00000000e+00+0.j,   5.98651912e-36+0.j]) # i.e., {2, 0}
        array([[ 0.00000000+0.70710678j,  0.70710678+0.j        ],
               [ 0.70710678+0.j        ,  0.00000000+0.70710678j]])
        
        Be careful about round-off error!
        
        >>> a = np.array([[1 + 1e-9, 0], [0, 1 - 1e-9]])
        >>> # Theor. e-values are 1 +/- 1e-9
        >>> w, v = LA.eig(a)
        >>> w; v
        array([ 1.,  1.])
        array([[ 1.,  0.],
               [ 0.,  1.]])
    


If the matrix is symmetric, the function `np.linalg.eigh()` is faster and more robust.


```python
# This is a hermitian matrix for testing the eigh() function
matrix2 = np.array([[1.,2.,3.],[2.,4.,5.],[3.,5.,6.]])
```


```python
print(matrix2)
```

    [[1. 2. 3.]
     [2. 4. 5.]
     [3. 5. 6.]]



```python
eigenvalues2, eigenvectors2 = np.linalg.eigh(matrix2)
```


```python
print(eigenvalues2)
```

    [-0.51572947  0.17091519 11.34481428]



```python
print(eigenvectors2)
```

    [[-0.73697623  0.59100905 -0.32798528]
     [-0.32798528 -0.73697623 -0.59100905]
     [ 0.59100905  0.32798528 -0.73697623]]


## Analytic eigenvalues/eigenvectors
Using the `sympy` library


```python
import sympy
```


```python
sympy.init_printing() # turn on pretty printing of math expressions
```

With `sympy` we have to first declare any variables that we wish to use.

Note the form below.  The names of the new variables appear twice.


```python
a, b, c = sympy.symbols('a, b, c')
```


```python
matrixA = sympy.Matrix([[a,b],[b,c]])
```


```python
matrixA
```


```python
# This returns the eigenvalues, their degeneracy, and the eigenvectors corresponding to each eigenvalue
matrixA.eigenvects()
```


```python
help(matrixA.eigenvects)
```

    Help on method eigenvects in module sympy.matrices.matrices:
    
    eigenvects(error_when_incomplete=True, iszerofunc=<function _iszero at 0x000001F9BD792598>, **flags) method of sympy.matrices.dense.MutableDenseMatrix instance
        Return list of triples (eigenval, multiplicity, basis).
        
        The flag ``simplify`` has two effects:
            1) if bool(simplify) is True, as_content_primitive()
            will be used to tidy up normalization artifacts;
            2) if nullspace needs simplification to compute the
            basis, the simplify flag will be passed on to the
            nullspace routine which will interpret it there.
        
        Parameters
        ==========
        
        error_when_incomplete : bool
            Raise an error when not all eigenvalues are computed. This is
            caused by ``roots`` not returning a full list of eigenvalues.
        
        If the matrix contains any Floats, they will be changed to Rationals
        for computation purposes, but the answers will be returned after being
        evaluated with evalf. If it is desired to removed small imaginary
        portions during the evalf step, pass a value for the ``chop`` flag.
    



```python

```

5f949fd30f348049b9747d927c96556c19546818
ipynb
Jupyter Notebook
Eigenvalues.ipynb
corcoted/Phys475
8fc0ee6bccda19e5afff14f0e8fda6aef7ee6d66
MIT
2021-03-10T04:30:46.000Z
2021-07-12T09:20:43.000Z
Eigenvalues.ipynb
corcoted/Phys475
8fc0ee6bccda19e5afff14f0e8fda6aef7ee6d66
MIT
Eigenvalues.ipynb
corcoted/Phys475
8fc0ee6bccda19e5afff14f0e8fda6aef7ee6d66
MIT
Qwen/Qwen-72B
1. YES
2. YES