---
jupytext:
  formats: ipynb,md:myst
  text_representation:
    extension: .md
    format_name: myst
    format_version: 0.13
    jupytext_version: 1.14.4
kernelspec:
  display_name: Python 3 (phys-555)
  language: python
  name: phys-555
---

```{code-cell} ipython3
:tags: [hide-cell]

import mmf_setup;mmf_setup.nbinit()
import logging;logging.getLogger('matplotlib').setLevel(logging.CRITICAL)
%matplotlib inline
import numpy as np, matplotlib.pyplot as plt
```

(sec:BlochSphere)=
# Bloch Sphere

The [Bloch sphere] is an extremely useful and accurate way of visualizing the
information in a [qubit].  Mathematically it is not so transparent, but it is very
intuitive.  Formally, we represent a quantum state $\ket{\psi}$ in [spherical
coordinates] as a point with angles $\theta$ and $\phi$ on the unit sphere
$r=1$:

:::{margin}
See {cite:p}`Nielsen:2010` (1.3) and {cite:p}`Williams:2011` (1.6).
:::
\begin{gather*}
  \ket{\psi} = 
  e^{\I\gamma}
  \Bigl(
    \cos\frac{\theta}{2}\ket{0}
    +
    e^{\I \phi}\sin\frac{\theta}{2}\ket{1}
  \Bigr)
  =
  e^{\I \gamma}
  \begin{pmatrix}
    \cos\frac{\theta}{2}\\
    e^{\I \phi}\sin\frac{\theta}{2}
  \end{pmatrix}, \\
  \begin{pmatrix}
    x\\
    y\\
    z
  \end{pmatrix} = 
  \begin{pmatrix}
    r\sin\phi\;\cos\phi\\
    r\sin\theta\;\sin\phi\\
    r\cos\theta
  \end{pmatrix}.
\end{gather*}


```{figure} https://upload.wikimedia.org/wikipedia/commons/6/6b/Bloch_sphere.svg
:figclass: margin

Bloch sphere representation of
\begin{gather*}
  \ket{\psi} = 
  \cos\frac{\theta}{2}\ket{0}
  +
  e^{\I \phi}\sin\frac{\theta}{2}\ket{1}
\end{gather*}
```

```{code-cell}
# :tags: [hide-input]

from qiskit.visualization import plot_bloch_vector


def get_vec(psi):
    """Return the Bloch vector from psi."""
    gamma = np.angle(psi[0])
    psi = np.exp(-1j*gamma) * np.asarray(psi)
    phi = np.angle(psi[1]) - np.angle(psi[0])
    theta = 2*np.arctan2(psi[0].real, 
                         (np.exp(-1j*phi)*psi[1]).real)
    x = np.sin(theta)*np.cos(phi)
    y = np.sin(theta)*np.sin(phi)
    z = np.cos(theta)
    return (x, y, z)
    
fig = plt.figure(figsize=(3*10, 10))
ax = fig.add_subplot(1, 3, 1, projection='3d')
plot_bloch_vector(get_vec([1, 1]), ax=ax, title=r"$|Ψ⟩ = \frac{|0⟩ + |1⟩}{\sqrt{2}}$")
ax = fig.add_subplot(1, 3, 2, projection='3d')
plot_bloch_vector(get_vec([1, -1]), ax=ax, title=r"$|Ψ⟩ = \frac{|0⟩ - |1⟩}{\sqrt{2}}$")
ax = fig.add_subplot(1, 3, 3, projection='3d')
plot_bloch_vector(get_vec([1, 1j]), ax=ax, title=r"$|Ψ⟩ = \frac{|0⟩ + \mathrm{i}|1⟩}{\sqrt{2}}$")
```

:::{note}

Some important questions:

1. Why does the phase $\gamma$ not affect the position on the Bloch sphere?
2. Why is the angle $\theta/2$, half of what one would normally use?
3. Related: Why are the "orthogonal" vectors $\ket{0}$ and $\ket{1}$ not at right
   angles?

{cite:p}`Williams:2011` has a nice discussion of these confusions in §1.3.3.
:::

## Intuitive Picture

The Bloch sphere is nice because it not only provides a complete and faithful
representation of a single qubit state, but arbitrary single-qubit operations (gates) have a
simple picture.  Specifically, any single-qubit gate can be expressed in terms of a
clockwise rotation $\vec{\theta} = \theta \uvec{n}$ of $\theta$ radians about an axis
$\uvec{n}$ as:

:::{margin}
This is (4.8) from {cite:p}`Nielsen:2010` with the notation $\mat{R_{\vec{\theta}}}
\equiv R_{\uvec{n}}(\theta)$.
:::
\begin{gather*}
  \mat{U} = \mat{R_{\vec{\theta}}} 
  = \exp\left(\vec{\theta}\cdot \frac{\vec{\mat{\sigma}}}{2\I}\right)
  = \cos\Bigl(\frac{\theta}{2}\Bigr)\;\mat{1} 
    - \I \sin\Bigl(\frac{\theta}{2}\Bigr) (n_x \mat{X} + n_y \mat{Y} + n_z \mat{Z}).
\end{gather*}

In terms of spin-½ particles, this is easily implemented using an external magnetic
field pointing in the $\uvec{n}$ direction.

In component form:

\begin{gather*}
  \mat{U} = \begin{pmatrix}
    u_0 & -u_1^*\\
    u_1 & u_0^*
  \end{pmatrix},\\
  =\begin{pmatrix}
    \cos\Bigl(\frac{\theta}{2}\Bigr) - \I\sin\Bigl(\frac{\theta}{2}\Bigr)n_z
    & - \I\sin\Bigl(\frac{\theta}{2}\Bigr)(n_x - \I n_y)\\
    - \I\sin\Bigl(\frac{\theta}{2}\Bigr)(n_x + \I n_y)
    & \cos\Bigl(\frac{\theta}{2}\Bigr) + \I\sin\Bigl(\frac{\theta}{2}\Bigr)n_z
  \end{pmatrix}
\end{gather*}

Alternatively, redefine $\theta = \omega$, express $\hat{n}$ in polar coordinates, and
let $\eta$ be the phase of $u_0$: 

\begin{gather*}
  \hat{n} = \begin{pmatrix}
    \sin\theta \cos\phi\\
    \sin\theta \sin\phi\\
    \cos\theta
  \end{pmatrix}, \qquad
  e^{\I\eta} = \frac{\cos(\frac{\omega}{2}) - \I\sin(\frac{\omega}{2})n_z}
  {\sqrt{\cos^2\tfrac{\omega}{2} + \sin^2\tfrac{\omega}{2}\;\cos^2\theta}},\\
  \mat{U} = \begin{pmatrix}
    \cos\tfrac{\omega}{2} - \I\sin\tfrac{\omega}{2}\cos\theta
    & - \I\sin\tfrac{\omega}{2}\sin\theta e^{-\I\phi}\\
    - \I\sin\tfrac{\omega}{2}\sin\theta e^{\I\phi}
    & \cos\tfrac{\omega}{2}+ \I\sin\tfrac{\omega}{2}\cos\theta
  \end{pmatrix}.
\end{gather*}

The magnitude of $u_0$ (the denominator of $e^{\I\eta}$ above) can be simplified by
introducing a new angle $\chi$, which describes how the vector $\ket{0}$ is rotated:

\begin{gather*}
  \sin\chi = \sin\tfrac{\omega}{2}\sin\theta,\\
  \begin{pmatrix}
   u_0\\
   u_1
  \end{pmatrix}
  =
  e^{\I\eta}
  \begin{pmatrix}
   \cos\chi\\
   -\I\sin\chi\; e^{\I\phi}
  \end{pmatrix}
  =
  \mat{U}\ket{0}.
\end{gather*}


# QuTiP

```{code-cell} ipython3
import qutip
b = qutip.Bloch()
b.make_sphere()
display(b)
```

[Bloch sphere]: <https://en.wikipedia.org/wiki/Bloch_sphere> 
[qubit]: <https://en.wikipedia.org/wiki/Qubit>
[spherical coordinates]: <https://en.wikipedia.org/wiki/Spherical_coordinate_system>

[section 4.5.2]: <https://ntserver1.wsulibs.wsu.edu:2171/lib/wsu/reader.action?docID=647366&ppg=225>
