diff --git a/examples/.ipynb_checkpoints/random_walk_tutorial-checkpoint.ipynb b/examples/.ipynb_checkpoints/random_walk_tutorial-checkpoint.ipynb
new file mode 100644
index 00000000000..6e954a725f5
--- /dev/null
+++ b/examples/.ipynb_checkpoints/random_walk_tutorial-checkpoint.ipynb
@@ -0,0 +1,766 @@
+{
+ "cells": [
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "# Quantum Random Walks With Cirq - Tutorial"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "**Classical Random Walks**\n",
+ "\n",
+ "A random walks is a random process involving a \"walker\" that is placed in some $n$-dimensional medium \n",
+ "(like a grid or a graph). We then repeatedly query some random variable, and based on the outcome of our measurement,\n",
+ "the walker's position vector (position on the graph or grid) is updated. A very basic example of a random walk is \n",
+ "the one-dimensional graphical case, where we consider a marker placed on the origin of a number line with markings\n",
+ "at each of the integers. Let the initial position vector of our marker be $\\lvert 0\\rangle$. For $N$ steps of our\n",
+ "random walk, so take a set of $N$ random variables, $\\{X_1, \\ ..., \\ X_N\\}$, which can take on either a value of \n",
+ "$1$ or $-1$ with equal probability ($0.5$). To find the updated position vector of our walker, we simply compute\n",
+ "the value:\n",
+ "\n",
+ "$$j \\ = \\ \\displaystyle\\sum_{k \\ = \\ 1}^{N} \\ X_k$$\n",
+ "\n",
+ "Where we know:\n",
+ "\n",
+ "\n",
+ "$$\\lvert \\text{Final}\\rangle \\ = \\ \\lvert \\text{Initial} \\ + \\ j\\rangle$$\n",
+ "\n",
+ "\n",
+ "So for our case, the final position vector is simply $\\lvert j\\rangle$. This model of a random walk can easily \n",
+ "be generalized to $n$-dimensions. Another important fact to note is that for a discrete, 1-dimensional random \n",
+ "walk on a number-line-like graph, the probability of the random walker being at a specific location follows \n",
+ "a binomial distribution. Let us define an $N$-step random walk. Let us then assert that $N \\ = \\ L \\ + \\ R$, \n",
+ "where $L$ is the number of steps to the left, and $R$ is the number of steps to the right. We can then reason \n",
+ "that if there is some probability $p_{r}$ of the walker taking a rightward step at one time-step of the random \n",
+ "walk, the probability of taking a leftward step is given by $1 \\ - \\ p_{r}$. It follows that the probability \n",
+ "of taking $L \\ = \\ N \\ - \\ R$ leftward steps, and $R$ rightward steps in a random walk of $N$ total steps is \n",
+ "given by:\n",
+ "\n",
+ "\n",
+ "$$P(N, \\ R) \\ = \\ p_{r}^R (1 \\ - \\ p_{r})^{N \\ - \\ R}$$\n",
+ "\n",
+ "\n",
+ "We then have to consider the probability that for an $N$ step random walk, our walker ends up at position \n",
+ "$X \\ = \\ L \\ - \\ R$. Well, we know the probability of taking $L$ left steps and $R$ right steps, and we know \n",
+ "that for a random walk of $N$ steps, the position of the walker is determined by the number of left steps, \n",
+ "minus the number of right steps. Since it doesn't matter the order in which the sequence of $N$ steps occurs, \n",
+ "to find the total probability of being at some location, $P(X)$, we have to multiply the probability $P(L, \\ R)$ \n",
+ "by the number of possible ways in which $L$ left steps and $R$ right steps can be arranged in a sequence. \n",
+ "Well, since we have $N$ total steps, we can \"choose\" $R$ of those steps to be allocated to rightward steps, \n",
+ "and automatically know that the remaining $N \\ - \\ R$ steps were left steps. We calculate $N$ \"choose\" $R$ \n",
+ "steps by calculating the binomial coefficient, therefore getting:\n",
+ "\n",
+ "\n",
+ "$$P_{N}(X) \\ = \\ \\begin{pmatrix} N \\\\ R \\end{pmatrix} \\ p_{r}^R (1 \\ - \\ p_{r})^{N \\ - \\ R}$\n",
+ "$\\Rightarrow \\ X \\ = \\ L \\ - \\ R \\ \\Rightarrow \\ P_{N}(X) \\ = \\ \\begin{pmatrix} N \\\\ \\frac{N \\ - \\ X}{2} \\end{pmatrix} \\ p_{r}^{\\frac{N \\ - \\ X}{2}} (1 \\ - \\ p_{r})^{\\frac{N \\ + \\ X}{2}}$$\n",
+ "\n",
+ "\n",
+ "And so we have shown that the probability distribution for the position of the walker for an $N$ step random \n",
+ "walk is given by a binomial distribution. This fact is important, as we will show that the probability \n",
+ "distribution that is created when a quantum random walk is simulated is nowhere close to the binomial \n",
+ "distribution that we expect to see for a classical 1-dimensional random walk.\n",
+ "\n",
+ "\n",
+ "\n",
+ "**Quantum Random Walks**\n",
+ "\n",
+ "\n",
+ "The process of the quantum random walk isn't that much different from its classical counterpart, although \n",
+ "the observed results of the two processes have many differences. First, let us motivate the creation of a \n",
+ "QRW. The idea is that when one performs analysis on a classical random walk, you can find that \n",
+ "$\\sigma^2 \\ \\sim \\ T$, where $\\sigma$ is the standard deviation of the random walk's probability distribution, \n",
+ "and $T$ is the number of time-steps of the random walk. For the quantum random walk, we can see that \n",
+ "$\\sigma^2 \\ \\sim \\ T^2$. In other words, the standard deviation grows at a quadratically faster rate. \n",
+ "At a high level, this signifies that the quantum walker \"spreads out\" quadratically faster than the \n",
+ "classical one, showing that the process of a QRW is quadratically faster than its classical counterpart.\n",
+ "\n",
+ "\n",
+ "In order to create a quantum random walk, we have to translate the components of the classical random walk \n",
+ "to a quantum problem. We can encode the position of a \"walker\" in some $n$ -dimensional space with a vector\n",
+ "$\\lvert j\\rangle$. For the purpose of this project, we will be investigating a very basic case of a \n",
+ "random walk on a ring-shaped graph, with adjacent nodes connected by a single edge. The configuration \n",
+ "looks something like this:\n",
+ "\n",
+ "\n",
+ "\n",
+ "\n",
+ "\n",
+ "Going back to our original idea of some position vector $\\lvert j\\rangle$, it is apparent that in order to \n",
+ "encode the location of a \"walker\" on this graph, we need to assign a specific value of our position vector \n",
+ "to each node. Well, this is fairly simple, for a graph of $K$ nodes, we form a Hilbert space\n",
+ "$H_W$ spanned by the following set:\n",
+ "\n",
+ "\n",
+ "$$H_W \\ = \\ \\{\\lvert j\\rangle \\ : \\ j \\ = \\ 0, \\ ..., \\ K \\ - \\ 1 \\}$$\n",
+ "\n",
+ "\n",
+ "We also require another vector in order to create a random walk. We need a \"coin vector\", which will encode \n",
+ "the direction in which the random walk will progress at the $T$-th step of the process. This Hilbert space \n",
+ "is spanned by the two basis states, representing forward and backward progression on our number-line-like \n",
+ "graph (actually, I guess our graph looks more like a ring, so I guess our two basis states will represent \n",
+ "clockwise and counter-clockwise motion, but it's the same idea). We will call this Hilbert space $H_C$, \n",
+ "and we can again define our spanning set:\n",
+ "\n",
+ "\n",
+ "$$H_C \\ = \\ \\{\\lvert i\\rangle \\ : \\ i \\ = \\ \\downarrow, \\ \\uparrow\\rangle\\}$$\n",
+ "\n",
+ "\n",
+ "Where the upward-arrow symbol represent counter-clockwise motion, and the downward arrow represents \n",
+ "clock-wise motion. Now that we have defined all of the vectors we need to encode the information about \n",
+ "our random walk, we must understand how we can realize these vectors in our quantum algorithm. Well, this is \n",
+ "again fairly simple. For a graph of $K \\ = \\ 2^n$ nodes, we require $n$ qubits to encode binary representations \n",
+ "of numbers ranging from $0$ to $K \\ - \\ 1$, therefore each of the vectors spanning $H_W$ will simply be given \n",
+ "by the binary representation of $j$ corresponding to the basis vector $\\lvert j\\rangle$. For the coin vector, \n",
+ "since we have only two states, we only need one qubit to encode the two possible states:\n",
+ "\n",
+ "\n",
+ "$$\\lvert 0\\rangle \\ = \\ \\lvert \\uparrow\\rangle \\ \\ \\text{and} \\ \\ \\lvert 1\\rangle \\ = \\ \\lvert \\downarrow\\rangle$$\n",
+ "\n",
+ "\n",
+ "In order to represent the total space of all possible states of our system, we take the tensor product of the \n",
+ "two spanning sets, which will then span the new Hilbert space $H_C \\ \\otimes \\ H_W$. We will write a general \n",
+ "element of this Hilbert space as $\\lvert i\\rangle \\ \\otimes \\ \\lvert j\\rangle$.\n",
+ "\n",
+ "Moving right along, we now require a method to evolve our random walk forward at each step. We define a random \n",
+ "walk evolution operator as follows:\n",
+ "\n",
+ "\n",
+ "$$U \\ = \\ \\lvert \\uparrow\\rangle\\langle\\uparrow\\lvert \\ \\otimes \\ \\displaystyle\\sum_{j} \\ \\lvert j \\ + \\ 1\\rangle\\langle j\\lvert \\ + \\ \\lvert \\downarrow\\rangle\\langle\\downarrow\\lvert \\ \\otimes \\ \\displaystyle\\sum_{j} \\ \\lvert j \\ - \\ 1\\rangle\\langle j\\lvert $$\n",
+ "\n",
+ "\n",
+ "By the way, I didn't come up with this genius operator, this came from the paper I referenced at the top of the \n",
+ "post. Essentially, since our qubits take on states $\\lvert 0\\rangle$ and $\\lvert 1\\rangle$, we know that \n",
+ "any possible, general basis state vector formed from qubits $\\lvert n\\rangle^{\\otimes \\ N}$ will be orthogonal to \n",
+ "all other vectors in the basis spanning the space. Because of this, we can create an operator that first \n",
+ "\"picks out\" the coin vector's state (the other term just goes to $0$, as, like I said, the states or orthogonal), \n",
+ "and then sums over all possible position states until it finds the position state to which the operator is \n",
+ "being applied. The inner product of the vector and itself is just one (the vectors are not only orthogonal, \n",
+ "they're orthonormal!), and the new position state of the vector is $\\lvert j \\ \\pm \\ 1\\rangle$, depending on \n",
+ "the state of the coin vector. This did exactly what we wanted, it evolved our random walk either forward or \n",
+ "backwards by one step! If you're still not convinced, let's check to see what happens when we have the state \n",
+ "$\\lvert \\uparrow\\rangle \\ \\otimes \\ \\lvert 1\\rangle$ and we apply the $U$ operator:\n",
+ "\n",
+ "\n",
+ " $$U (\\lvert \\uparrow\\rangle \\ \\otimes \\ \\lvert 1\\rangle) \\ \\ = \\ \\Big( \\ \\lvert \\uparrow\\rangle\\langle\\uparrow\\lvert \\ \\otimes \\ \\displaystyle\\sum_{j} \\ \\lvert j \\ + \\ 1\\rangle\\langle j\\lvert \\ + \\ \\lvert \\downarrow\\rangle\\langle\\downarrow\\lvert \\ \\otimes \\ \\displaystyle\\sum_{j} \\ \\lvert j \\ - \\ 1\\rangle\\langle j\\lvert \\Big )(\\lvert \\uparrow\\rangle \\ \\otimes \\ \\lvert 1\\rangle)$$\n",
+ " \n",
+ " $$\\Rightarrow \\ \\lvert \\uparrow\\rangle\\langle\\uparrow\\lvert \\uparrow\\rangle \\ \\otimes \\ \\displaystyle\\sum_{j} \\ \\lvert j \\ + \\ 1\\rangle\\langle j\\lvert 1\\rangle \\ + \\ \\lvert \\downarrow\\rangle\\langle\\downarrow\\lvert \\uparrow\\rangle \\ \\otimes \\ \\displaystyle\\sum_{j} \\ \\lvert j \\ - \\ 1\\rangle\\langle j\\lvert 1\\rangle$$\n",
+ "\n",
+ "\n",
+ " $$\\Rightarrow \\ \\lvert \\uparrow\\rangle \\ \\otimes \\ \\lvert 2\\rangle \\ + \\ 0\\lvert \\downarrow\\rangle \\ \\otimes \\ \\lvert 0\\rangle \\ = \\ \\lvert \\uparrow\\rangle \\ \\otimes \\ \\lvert 2\\rangle$$\n",
+ "\n",
+ "\n",
+ " As you can see, it works! Now, we must consider the randomness of the random walk. For the purposes of our \n",
+ " random walk, we will set $p_{r} \\ = \\ 0.5$, and therefore make $p_{l} \\ = \\ 0.5$ as well. At each time step, \n",
+ " it is necessary that we randomly flip the state of our coin vector $\\lvert i\\rangle$. The Hadamard \n",
+ " transformation seems like a natural choice, as:\n",
+ "\n",
+ "\n",
+ " $$H \\ = \\ \\frac{1}{\\sqrt{2}}\\begin{pmatrix} 1 && 1 \\\\ 1 && -1 \\end{pmatrix} \\ \\Rightarrow \\ H \\lvert \\uparrow\\rangle \\ = \\ \\frac{\\lvert \\uparrow\\rangle \\ + \\ \\lvert \\downarrow\\rangle }{\\sqrt{2}} \\ \\Rightarrow \\ H \\lvert \\downarrow\\rangle \\ = \\ \\frac{\\lvert \\uparrow\\rangle \\ - \\ \\lvert \\downarrow\\rangle }{\\sqrt{2}}$$\n",
+ "\n",
+ "\n",
+ " The probability of measuring one of the basis states is given by squaring the coefficient in the linear combination, which we can see for both outcomes is equal to $0.5$, the same probability of a step to the \n",
+ " right/step to the left that we originally desired. We can now combine our operators into one \"master operator\" \n",
+ " that works as one complete step of the random walk, including randomizing the coin vector:\n",
+ "\n",
+ "\n",
+ " $$S \\ = \\ U \\ (H \\ \\otimes \\ I)$$\n",
+ "\n",
+ "\n"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "**Tutorial: Building a QRW With Cirq**\n",
+ "\n",
+ "\n",
+ "Now, that we have established all of the necessary mathematical rigour to create a quantum random walk, we \n",
+ "need to translate this into code. We can start by creating a qubit register, which will be used to represent \n",
+ "all of the position vectors on our graph. Recall that for an $N$ qubit register, we can encode all numbers \n",
+ "ranging from $0$ to $2^N \\ - \\ 1$. For now, we will set $N \\ = \\ 7$:"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 2,
+ "metadata": {},
+ "outputs": [
+ {
+ "name": "stdout",
+ "output_type": "stream",
+ "text": [
+ "[cirq.GridQubit(0, 0), cirq.GridQubit(0, 1), cirq.GridQubit(0, 2), cirq.GridQubit(0, 3), cirq.GridQubit(0, 4), cirq.GridQubit(0, 5), cirq.GridQubit(0, 6)]\n"
+ ]
+ }
+ ],
+ "source": [
+ "import cirq\n",
+ "import random\n",
+ "import numpy as np\n",
+ "import copy\n",
+ "import sympy\n",
+ "import itertools\n",
+ "from matplotlib import pyplot as plt\n",
+ "\n",
+ "number_qubits = 7\n",
+ "\n",
+ "qubits = []\n",
+ "for i in range(0, number_qubits):\n",
+ " qubits.append(cirq.GridQubit(0, i))\n",
+ "\n",
+ "print(qubits)"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "Next, we have to initialize our qubit register into some initial state. This can vary quite a bit, depending on \n",
+ "the simulation that we want to make. To start, let's say that our initial position vector for our \"random walker\" \n",
+ "is roughly in the middle of the graph (not exactly, as we have an even number of position vector values). Let's \n",
+ "also say that our coin vector is initialized in the $|\\downarrow\\rangle$ state. Since $|\\downarrow\\rangle$ corresponds to $|1\\rangle$, the only operations that have to be performed in this qubit initialization method is \n",
+ "an $X$ gate acting on ``GridQubit(0, 1)`` (initializing the position vector), as well as an $X$ gate acting on \n",
+ "the coin qubit:"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 3,
+ "metadata": {},
+ "outputs": [],
+ "source": [
+ "def initial_state():\n",
+ "\n",
+ " yield cirq.X.on(cirq.GridQubit(0, 1))\n",
+ " yield cirq.X.on(cirq.GridQubit(0, number_qubits))"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "Now that we have created and initialized our qubit register, we have to create an operation that can evolve \n",
+ "our random walk forward by one step. At a high level, our evolution operation will follow this process:\n",
+ "\n",
+ "1. \"Flip\" the coin qubit. The result of this \"flip\" will tell us in which direction our random walker should move. This \"flip\" operation is nothing more than a Hadamard transformation applied to the coin qubit after each evolution operation.\n",
+ "\n",
+ "\n",
+ "2. Based on the state of the coin qubit after the flip, either perform the operation $|j\\rangle \\ \\rightarrow \\ |j \\ + \\ 1\\rangle$ or $|j\\rangle \\ \\rightarrow \\ |j \\ - \\ 1\\rangle$ on the register of qubits encoding the position vector of the random walker on the graph. This will involve having two operations controlled by opposite states of the coin quibt, each representing a step forward or a step backward on the graph. Thus, our evolution operation will look something like this:\n",
+ "\n",
+ "\n",
+ "\n",
+ "\n",
+ "If we construct our evolution operator in this fashion, the coin qubit is able to dictate whether the walker \n",
+ "steps forwards or backwards without ever having to be measured!\n",
+ "\n",
+ "\n",
+ "Now that we have a high-level setup for our evolution operator, we have to construct the \"step forward\" and \n",
+ "\"step backward\" operations. These are nothing more than an addition and a subtraction operator, each of with \n",
+ "adds or substracts $1$ from the position vector. \n",
+ "\n",
+ "\n",
+ "Before we actually dive into making the addition and substraction operators, it will be useful for us to define \n",
+ "an operation which we will call an n-qubit Toffoli gate. The name is pretty self-explanatory, it is just \n",
+ "an $X$ gate that is controlled by an arbitrary number of qubits $n$, rather than only $1$ or $2$ in the \n",
+ "standard $CNOT$ and Toffoli gates.\n",
+ "\n",
+ "\n",
+ "In order to implement this, we have to use a series of Toffoli gates, along with a collection of ancilla \n",
+ "qubits ($n \\ - \\ 1$) ancilla qubits to be exact:"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 4,
+ "metadata": {},
+ "outputs": [
+ {
+ "name": "stdout",
+ "output_type": "stream",
+ "text": [
+ "[cirq.GridQubit(1, 0), cirq.GridQubit(1, 1), cirq.GridQubit(1, 2), cirq.GridQubit(1, 3), cirq.GridQubit(1, 4), cirq.GridQubit(1, 5), cirq.GridQubit(1, 6)]\n"
+ ]
+ }
+ ],
+ "source": [
+ "ancilla = []\n",
+ "for i in range(0, number_qubits):\n",
+ " ancilla.append(cirq.GridQubit(1, i))\n",
+ "\n",
+ "print(ancilla)"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "We start by applying a Toffoli gate to the first two control qubits, with the target as the first ancilla \n",
+ "qubit. Then, we apply a Toffoli controlled by the third control qubit and the first ancilla qubit, which we \n",
+ "targetted with the previous Toffoli gate. We continue this process until all control qubits have been utilized \n",
+ "in Toffoli gates, and then attach a $CNOT$ gate to our final ancilla qubit, targetting the \"overall\" original \n",
+ "target qubit of the $n$-qubit Toffoli gate. Our final step is to perform an uncomputation operation, \n",
+ "which means that we apply our series of Toffoli gates in reverse. This allows us to revert our ancilla back to \n",
+ "its initial state $|0\\rangle^{\\otimes n \\ - \\ 1}$, thus allowing it to be re-used for future computation.\n",
+ "\n",
+ "\n",
+ "This process may seem a little bit confusing, but here is an example of the generated circuit for the \n",
+ "$n$-qubit Toffoli gate for the case of $n \\ = \\ 4$, when this process is implemented in Cirq:"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 5,
+ "metadata": {},
+ "outputs": [
+ {
+ "name": "stdout",
+ "output_type": "stream",
+ "text": [
+ "(0, 0): ───@───────────────────────@───\n",
+ " │ │\n",
+ "(0, 1): ───@───────────────────────@───\n",
+ " │ │\n",
+ "(0, 2): ───┼───@───────────────@───┼───\n",
+ " │ │ │ │\n",
+ "(0, 3): ───┼───┼───@───────@───┼───┼───\n",
+ " │ │ │ │ │ │\n",
+ "(0, 4): ───┼───┼───┼───X───┼───┼───┼───\n",
+ " │ │ │ │ │ │ │\n",
+ "(1, 0): ───X───@───┼───┼───┼───@───X───\n",
+ " │ │ │ │ │\n",
+ "(1, 1): ───────X───@───┼───@───X───────\n",
+ " │ │ │\n",
+ "(1, 2): ───────────X───@───X───────────\n"
+ ]
+ }
+ ],
+ "source": [
+ "number_qubits = 4\n",
+ "\n",
+ "def apply_n_qubit_tof(ancilla, args):\n",
+ "\n",
+ " if (len(args) == 2):\n",
+ " yield cirq.CNOT.on(args[0], args[1])\n",
+ "\n",
+ " elif (len(args) == 3):\n",
+ " yield cirq.CCX.on(args[0], args[1], args[2])\n",
+ "\n",
+ " else:\n",
+ "\n",
+ " yield cirq.CCX.on(args[0], args[1], ancilla[0])\n",
+ " for k in range(2, len(args)-1):\n",
+ " yield cirq.CCX(args[k], ancilla[k-2], ancilla[k-1])\n",
+ "\n",
+ " yield cirq.CNOT.on(ancilla[len(args)-3], args[len(args)-1])\n",
+ "\n",
+ " for k in range(len(args)-2, 1, -1):\n",
+ " yield cirq.CCX(args[k], ancilla[k-2], ancilla[k-1])\n",
+ " yield cirq.CCX.on(args[0], args[1], ancilla[0])\n",
+ "\n",
+ "\n",
+ "control = [cirq.GridQubit(0, i) for i in range(0, number_qubits+1)]\n",
+ "circuit = cirq.Circuit()\n",
+ "circuit.append(apply_n_qubit_tof(ancilla, control))\n",
+ "print(circuit)"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "The reason why I have introduced an extra qubit is because the way that I coded this function takes the last entry \n",
+ "in the ``args`` list as the target qubit, thus I needed $4$ control qubits, plus $1$ target qubit for a total \n",
+ "of $5$ qubits in the ``control`` list (even though one of them is actually the target!)."
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "Now we can get back to creating the addition and substraction operators. Starting with the addition operator, \n",
+ "the idea is:\n",
+ "\n",
+ "\n",
+ "\n",
+ "1. Have a $CNOT$ gate controlled by the coin qubit targetting the least significant qubit. This means that if the coin qubit is in the \"move forward\" state, the addition operator will be activated.\n",
+ "\n",
+ "\n",
+ "2. Apply an $X$ gate to the qubit that was just targetted by the $CNOT$ gate.\n",
+ "\n",
+ "\n",
+ "3. Apply a Toffoli gate controlled by the coin qubit and the qubit on which the $X$ gate was just placed, targetting the second least-significant qubit. This acts as a \"carry operation\", meaning that if the coin qubit is in the addition state, and the least significant qubit is in the $|0\\rangle$ state (meaning it was in the $|1\\rangle$ state, but had the $CNOT$ operation applied to it, we had to apply the $X$ gate to flip it back to the $|1\\rangle$ state so it can activate the Toffoli gate), then flip the value of the next qubit, signifying that the addition mod $2$ carried over a one to the next digit of the number.\n",
+ "\n",
+ "\n",
+ "4. Continue this process with $n$-qubit Toffoli gates controlled by all qubits less significant than the target qubit, along with the coin qubit until all qubits have had Toffoli gates applied.\n",
+ "\n",
+ "\n",
+ "5. Apply $X$ gates to all qubits in the position vector register, as they all had $X$ gates applied to them in the process of addition.\n",
+ "\n",
+ "For the subtraction operator, we can make use of the fact that quantum operations are reversible, meaning that if \n",
+ "we have some addition unitary $A$, such that $A |j\\rangle \\ = \\ |j \\ + \\ 1\\rangle$, then:\n",
+ "\n",
+ "\n",
+ "$$A^{\\dagger}A |j\\rangle \\ = \\ A^{\\dagger}|j \\ + \\ 1\\rangle \\ \\Rightarrow \\ A^{\\dagger}|j \\ + \\ 1\\rangle \\ = \\ |j\\rangle \\ \\Rightarrow \\ A^{\\dagger}|k\\rangle \\ = \\ |k \\ - \\ 1\\rangle$$\n",
+ "\n",
+ "\n",
+ "And so this means that $S \\ = \\ A^{\\dagger}$. Since we can decompose $A$ into a product of a bunch of unitaries, \n",
+ "we get:\n",
+ "\n",
+ "\n",
+ " $$A \\ = \\ U_1 U_2 \\ ... \\ U_n \\ \\Rightarrow \\ S \\ = \\ A^{\\dagger} \\ = \\ U_n^{\\dagger} U_{n - 1}^{\\dagger} \\ ... \\ U_{1}^{\\dagger}$$\n",
+ "\n",
+ "\n",
+ "But our method only uses $X$ gates and controlled $X$ gates, all of which are Hermitian, thus we have:\n",
+ "\n",
+ "\n",
+ "$$S \\ = \\ U_n^{\\dagger} U_{n - 1}^{\\dagger} \\ ... \\ U_{1}^{\\dagger} \\ = \\ U_n U_{n - 1} \\ ... \\ U_{1}$$\n",
+ "\n",
+ "\n",
+ "So basically, our subtraction operation will just be applying our addition operator, but with the order of \n",
+ "gates reversed. This allows us to create one general \"evolution operation\" for our random walk, which adds \n",
+ "or substract $1$ to the random walkers position vector, based on the coin qubit:"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 13,
+ "metadata": {},
+ "outputs": [],
+ "source": [
+ "def walk_step():\n",
+ "\n",
+ " #\"Flip\" the coin vector\n",
+ "\n",
+ " yield cirq.H.on(cirq.GridQubit(0, number_qubits))\n",
+ "\n",
+ " #Implement the Addition Operator\n",
+ "\n",
+ " yield cirq.X.on(cirq.GridQubit(0, number_qubits))\n",
+ "\n",
+ " for i in range(number_qubits, 0, -1):\n",
+ "\n",
+ " yield apply_n_qubit_tof(ancilla, [cirq.GridQubit(0, v) for v in range(number_qubits, i-2, -1)])\n",
+ " yield cirq.X.on(cirq.GridQubit(0, i-1))\n",
+ "\n",
+ " for i in range(number_qubits, 0, -1):\n",
+ " yield cirq.X.on(cirq.GridQubit(0, i-1))\n",
+ "\n",
+ " yield cirq.X.on(cirq.GridQubit(0, number_qubits))\n",
+ "\n",
+ " #Implement the Substraction Operator\n",
+ "\n",
+ " for i in range(number_qubits, 0, -1):\n",
+ " yield cirq.X.on(cirq.GridQubit(0, i-1))\n",
+ "\n",
+ " for i in range(1, number_qubits+1):\n",
+ "\n",
+ " yield apply_n_qubit_tof(ancilla, [cirq.GridQubit(0, v) for v in range(number_qubits, i-2, -1)])\n",
+ " yield cirq.X.on(cirq.GridQubit(0, i-1))"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "Next, we have to append these operations to our quantum circuit, specifically iteratively apply the \n",
+ "``walk_step()`` function in order to evolve our random walk forward. After we do this, we measure of position \n",
+ "vector qubit register, by applying measurement gates, and we sample our circuit repeatedly. In code, for the \n",
+ "example of $10$ iteration of our evolution operator, $200$ samples of the circuit, and $7$ position vector \n",
+ "qubits, we have:"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 7,
+ "metadata": {},
+ "outputs": [
+ {
+ "name": "stdout",
+ "output_type": "stream",
+ "text": [
+ "Counter({12: 50, 14: 24, 20: 16, 10: 15, 16: 13, 52: 12, 42: 8, 22: 7, 34: 7, 24: 6, 48: 5, 32: 5, 30: 4, 54: 4, 40: 4, 36: 4, 38: 4, 18: 3, 46: 3, 26: 3, 44: 2, 50: 1})\n"
+ ]
+ }
+ ],
+ "source": [
+ "number_qubits = 7\n",
+ "iterator = 30\n",
+ "sample_number = 200\n",
+ "\n",
+ "circuit = cirq.Circuit()\n",
+ "\n",
+ "circuit.append(initial_state())\n",
+ "\n",
+ "for j in range(0, iterator):\n",
+ " circuit.append(walk_step())\n",
+ "circuit.append(cirq.measure(*qubits, key='x'))\n",
+ "\n",
+ "simulator = cirq.Simulator()\n",
+ "result = simulator.run(circuit, repetitions=sample_number)\n",
+ "final = result.histogram(key='x')\n",
+ "\n",
+ "print(final)"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "Finally, we then graph the results of our simulation, with final position vector value on the x-axis and the \n",
+ "number of occurences of that position vector value on the y-axis. This gives us a probability distribution for \n",
+ "the position of the random walker. It is important to note that the graphs will only have either even or odd \n",
+ "numbered data point, depending on the initial position of the walker and the number of steps taken:"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 8,
+ "metadata": {},
+ "outputs": [
+ {
+ "data": {
+ "image/png": "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\n",
+ "text/plain": [
+ ""
+ ]
+ },
+ "metadata": {
+ "needs_background": "light"
+ },
+ "output_type": "display_data"
+ }
+ ],
+ "source": [
+ "x_arr = [j for j in dict(final).keys()]\n",
+ "y_arr = [dict(final)[j] for j in dict(final).keys()]\n",
+ "\n",
+ "x_arr_final = []\n",
+ "y_arr_final = []\n",
+ "\n",
+ "while (len(x_arr) > 0):\n",
+ "\n",
+ " x_arr_final.append(min(x_arr))\n",
+ " y_arr_final.append(y_arr[x_arr.index(min(x_arr))])\n",
+ " holder = x_arr.index(min(x_arr))\n",
+ " del x_arr[holder]\n",
+ " del y_arr[holder]\n",
+ "\n",
+ "plt.plot(x_arr_final, y_arr_final)\n",
+ "plt.scatter(x_arr_final, y_arr_final)\n",
+ "plt.show()"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "As you can see, we get a pretty strange probability distribution! This is due to the fact that repeated \n",
+ "applications of the Hadamard gate to the coin qubit (which you may recall was initialized in the $|\\downarrow\\rangle$ state). Over time, interference causes our coin qubit to bias to the left, but also creates a small bump far to \n",
+ "the right as well! If you think this is weird, do the math! Take a qubit in the initial state of $|1\\rangle$ \n",
+ "and repeatedlly apply a Hadamard transformation, then calculate the probabilities of measuring $|0\\rangle$ \n",
+ "and $|1\\rangle$ by taking the modulus squared of the probability amplitude corresponding to each of the states. \n",
+ "In fact, let's see what happens when our qubit is initialized in the $|\\uparrow\\rangle$ state: "
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 10,
+ "metadata": {},
+ "outputs": [
+ {
+ "name": "stdout",
+ "output_type": "stream",
+ "text": [
+ "Counter({52: 46, 50: 21, 44: 15, 12: 14, 54: 12, 42: 8, 48: 7, 16: 6, 10: 6, 40: 6, 32: 6, 30: 6, 26: 6, 46: 6, 38: 5, 34: 5, 36: 5, 22: 5, 28: 4, 14: 3, 24: 3, 56: 2, 18: 2, 20: 1})\n"
+ ]
+ },
+ {
+ "data": {
+ "image/png": "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\n",
+ "text/plain": [
+ ""
+ ]
+ },
+ "metadata": {
+ "needs_background": "light"
+ },
+ "output_type": "display_data"
+ }
+ ],
+ "source": [
+ "def initial_state():\n",
+ "\n",
+ " yield cirq.X.on(cirq.GridQubit(0, 1))\n",
+ "\n",
+ "number_qubits = 7\n",
+ "iterator = 30\n",
+ "sample_number = 200\n",
+ "\n",
+ "circuit = cirq.Circuit()\n",
+ "\n",
+ "circuit.append(initial_state())\n",
+ "\n",
+ "for j in range(0, iterator):\n",
+ " circuit.append(walk_step())\n",
+ "circuit.append(cirq.measure(*qubits, key='x'))\n",
+ "\n",
+ "simulator = cirq.Simulator()\n",
+ "result = simulator.run(circuit, repetitions=sample_number)\n",
+ "final = result.histogram(key='x')\n",
+ "\n",
+ "print(final)\n",
+ "\n",
+ "x_arr = [j for j in dict(final).keys()]\n",
+ "y_arr = [dict(final)[j] for j in dict(final).keys()]\n",
+ "\n",
+ "x_arr_final = []\n",
+ "y_arr_final = []\n",
+ "\n",
+ "while (len(x_arr) > 0):\n",
+ "\n",
+ " x_arr_final.append(min(x_arr))\n",
+ " y_arr_final.append(y_arr[x_arr.index(min(x_arr))])\n",
+ " holder = x_arr.index(min(x_arr))\n",
+ " del x_arr[holder]\n",
+ " del y_arr[holder]\n",
+ "\n",
+ "plt.plot(x_arr_final, y_arr_final)\n",
+ "plt.scatter(x_arr_final, y_arr_final)\n",
+ "plt.show()"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "Cool, right!? It's the mirror image of what we saw when the coin qubit was in the other state. Let's try one \n",
+ "more thing, let's initialize our coin qubit in a \"balanced\" state, where interference doesn't bias our \n",
+ "distribution towards only one side! We will set our initial state to:\n",
+ "\n",
+ "\n",
+ "$$|i\\rangle \\ = \\ \\frac{|\\uparrow\\rangle \\ + \\ i|\\downarrow\\rangle}{\\sqrt{2}}$$\n",
+ "\n",
+ "\n",
+ "This is easily implemented by applying a Hadamard gate to $|\\uparrow\\rangle$, and then applying an $S$ gate to \n",
+ "the qubit. When we simulate this with Cirq, we get:"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 11,
+ "metadata": {},
+ "outputs": [
+ {
+ "name": "stdout",
+ "output_type": "stream",
+ "text": [
+ "Counter({52: 31, 12: 26, 20: 13, 10: 12, 54: 10, 14: 10, 46: 9, 48: 9, 30: 8, 16: 8, 42: 8, 50: 7, 22: 6, 34: 6, 38: 6, 28: 5, 40: 4, 44: 4, 32: 4, 36: 4, 26: 3, 24: 3, 18: 2, 56: 1, 8: 1})\n"
+ ]
+ },
+ {
+ "data": {
+ "image/png": "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\n",
+ "text/plain": [
+ ""
+ ]
+ },
+ "metadata": {
+ "needs_background": "light"
+ },
+ "output_type": "display_data"
+ }
+ ],
+ "source": [
+ "def initial_state():\n",
+ "\n",
+ " yield cirq.X.on(cirq.GridQubit(0, 1))\n",
+ " \n",
+ " yield cirq.H.on(cirq.GridQubit(0, number_qubits))\n",
+ " yield cirq.S.on(cirq.GridQubit(0, number_qubits))\n",
+ "\n",
+ "number_qubits = 7\n",
+ "iterator = 30\n",
+ "sample_number = 200\n",
+ "\n",
+ "circuit = cirq.Circuit()\n",
+ "\n",
+ "circuit.append(initial_state())\n",
+ "\n",
+ "for j in range(0, iterator):\n",
+ " circuit.append(walk_step())\n",
+ "circuit.append(cirq.measure(*qubits, key='x'))\n",
+ "\n",
+ "simulator = cirq.Simulator()\n",
+ "result = simulator.run(circuit, repetitions=sample_number)\n",
+ "final = result.histogram(key='x')\n",
+ "\n",
+ "print(final)\n",
+ "\n",
+ "x_arr = [j for j in dict(final).keys()]\n",
+ "y_arr = [dict(final)[j] for j in dict(final).keys()]\n",
+ "\n",
+ "x_arr_final = []\n",
+ "y_arr_final = []\n",
+ "\n",
+ "while (len(x_arr) > 0):\n",
+ "\n",
+ " x_arr_final.append(min(x_arr))\n",
+ " y_arr_final.append(y_arr[x_arr.index(min(x_arr))])\n",
+ " holder = x_arr.index(min(x_arr))\n",
+ " del x_arr[holder]\n",
+ " del y_arr[holder]\n",
+ "\n",
+ "plt.plot(x_arr_final, y_arr_final)\n",
+ "plt.scatter(x_arr_final, y_arr_final)\n",
+ "plt.show()"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "So we get a probability distribution that is much more symetric!\n",
+ "\n",
+ "\n",
+ "Random walks have applications in so many fields of scientfific inquiry, ranging from biology, to \n",
+ "computer science, to finance. I definitely think there are a lot of possible great extensions to this basic \n",
+ "example of a QRW and many more great projects that can be made by utilizing this interesting process! \n",
+ "\n",
+ "**References**\n",
+ "\n",
+ "The first section of this tutorial was taken from this blog post (written by the same person who wrote this tutorial): https://lucaman99.github.io/blog/2019/08/03/Quantum-Random-Walks.html\n",
+ "\n",
+ "For more information about quantum random walks, see: https://arxiv.org/abs/quant-ph/0303081\n",
+ "\n",
+ "For more information about applications of random walks, see: https://en.wikipedia.org/wiki/Random_walk#Applications\n",
+ "\n"
+ ]
+ }
+ ],
+ "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.6.8"
+ }
+ },
+ "nbformat": 4,
+ "nbformat_minor": 2
+}
diff --git a/examples/assets/circ2.png b/examples/assets/circ2.png
new file mode 100644
index 00000000000..21e2273f8ba
Binary files /dev/null and b/examples/assets/circ2.png differ
diff --git a/examples/assets/cycle.png b/examples/assets/cycle.png
new file mode 100644
index 00000000000..89ce420986b
Binary files /dev/null and b/examples/assets/cycle.png differ
diff --git a/examples/notebook_tutorials/new_test.py b/examples/notebook_tutorials/new_test.py
new file mode 100644
index 00000000000..232e3676839
--- /dev/null
+++ b/examples/notebook_tutorials/new_test.py
@@ -0,0 +1,57 @@
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+import os
+
+import pytest
+
+import nbformat
+
+
+def find_examples_jupyter_notebook_paths():
+ examples_folder = os.path.dirname(__file__)
+ for filename in os.listdir(examples_folder):
+ if not filename.endswith('.ipynb'):
+ continue
+ yield os.path.join(examples_folder, filename)
+
+
+@pytest.mark.parametrize('path', find_examples_jupyter_notebook_paths())
+
+def test_can_run_examples_jupyter_notebook(path):
+ notebook = nbformat.read(path, nbformat.NO_CONVERT)
+ state = {} # type: Dict[str, Any]
+
+ for cell in notebook.cells:
+ if cell.cell_type == 'code' and not is_matplotlib_cell(cell):
+ try:
+ exec(strip_magics_and_shows(cell.source), state)
+ # coverage: ignore
+ except:
+ print('Failed to run {}.'.format(path))
+ raise
+
+
+def is_matplotlib_cell(cell):
+ return "%matplotlib" in cell.source
+
+
+def strip_magics_and_shows(text):
+ """Remove Jupyter magics and pyplot show commands."""
+ lines = [line for line in text.split('\n')
+ if not contains_magic_or_show(line)]
+ return '\n'.join(lines)
+
+def contains_magic_or_show(line):
+ return (line.strip().startswith('%') or
+ 'pyplot.show(' in line or
+ 'plt.show(' in line)
diff --git a/examples/notebook_tutorials/random_walk_tutorial.ipynb b/examples/notebook_tutorials/random_walk_tutorial.ipynb
new file mode 100644
index 00000000000..6e954a725f5
--- /dev/null
+++ b/examples/notebook_tutorials/random_walk_tutorial.ipynb
@@ -0,0 +1,766 @@
+{
+ "cells": [
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "# Quantum Random Walks With Cirq - Tutorial"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "**Classical Random Walks**\n",
+ "\n",
+ "A random walks is a random process involving a \"walker\" that is placed in some $n$-dimensional medium \n",
+ "(like a grid or a graph). We then repeatedly query some random variable, and based on the outcome of our measurement,\n",
+ "the walker's position vector (position on the graph or grid) is updated. A very basic example of a random walk is \n",
+ "the one-dimensional graphical case, where we consider a marker placed on the origin of a number line with markings\n",
+ "at each of the integers. Let the initial position vector of our marker be $\\lvert 0\\rangle$. For $N$ steps of our\n",
+ "random walk, so take a set of $N$ random variables, $\\{X_1, \\ ..., \\ X_N\\}$, which can take on either a value of \n",
+ "$1$ or $-1$ with equal probability ($0.5$). To find the updated position vector of our walker, we simply compute\n",
+ "the value:\n",
+ "\n",
+ "$$j \\ = \\ \\displaystyle\\sum_{k \\ = \\ 1}^{N} \\ X_k$$\n",
+ "\n",
+ "Where we know:\n",
+ "\n",
+ "\n",
+ "$$\\lvert \\text{Final}\\rangle \\ = \\ \\lvert \\text{Initial} \\ + \\ j\\rangle$$\n",
+ "\n",
+ "\n",
+ "So for our case, the final position vector is simply $\\lvert j\\rangle$. This model of a random walk can easily \n",
+ "be generalized to $n$-dimensions. Another important fact to note is that for a discrete, 1-dimensional random \n",
+ "walk on a number-line-like graph, the probability of the random walker being at a specific location follows \n",
+ "a binomial distribution. Let us define an $N$-step random walk. Let us then assert that $N \\ = \\ L \\ + \\ R$, \n",
+ "where $L$ is the number of steps to the left, and $R$ is the number of steps to the right. We can then reason \n",
+ "that if there is some probability $p_{r}$ of the walker taking a rightward step at one time-step of the random \n",
+ "walk, the probability of taking a leftward step is given by $1 \\ - \\ p_{r}$. It follows that the probability \n",
+ "of taking $L \\ = \\ N \\ - \\ R$ leftward steps, and $R$ rightward steps in a random walk of $N$ total steps is \n",
+ "given by:\n",
+ "\n",
+ "\n",
+ "$$P(N, \\ R) \\ = \\ p_{r}^R (1 \\ - \\ p_{r})^{N \\ - \\ R}$$\n",
+ "\n",
+ "\n",
+ "We then have to consider the probability that for an $N$ step random walk, our walker ends up at position \n",
+ "$X \\ = \\ L \\ - \\ R$. Well, we know the probability of taking $L$ left steps and $R$ right steps, and we know \n",
+ "that for a random walk of $N$ steps, the position of the walker is determined by the number of left steps, \n",
+ "minus the number of right steps. Since it doesn't matter the order in which the sequence of $N$ steps occurs, \n",
+ "to find the total probability of being at some location, $P(X)$, we have to multiply the probability $P(L, \\ R)$ \n",
+ "by the number of possible ways in which $L$ left steps and $R$ right steps can be arranged in a sequence. \n",
+ "Well, since we have $N$ total steps, we can \"choose\" $R$ of those steps to be allocated to rightward steps, \n",
+ "and automatically know that the remaining $N \\ - \\ R$ steps were left steps. We calculate $N$ \"choose\" $R$ \n",
+ "steps by calculating the binomial coefficient, therefore getting:\n",
+ "\n",
+ "\n",
+ "$$P_{N}(X) \\ = \\ \\begin{pmatrix} N \\\\ R \\end{pmatrix} \\ p_{r}^R (1 \\ - \\ p_{r})^{N \\ - \\ R}$\n",
+ "$\\Rightarrow \\ X \\ = \\ L \\ - \\ R \\ \\Rightarrow \\ P_{N}(X) \\ = \\ \\begin{pmatrix} N \\\\ \\frac{N \\ - \\ X}{2} \\end{pmatrix} \\ p_{r}^{\\frac{N \\ - \\ X}{2}} (1 \\ - \\ p_{r})^{\\frac{N \\ + \\ X}{2}}$$\n",
+ "\n",
+ "\n",
+ "And so we have shown that the probability distribution for the position of the walker for an $N$ step random \n",
+ "walk is given by a binomial distribution. This fact is important, as we will show that the probability \n",
+ "distribution that is created when a quantum random walk is simulated is nowhere close to the binomial \n",
+ "distribution that we expect to see for a classical 1-dimensional random walk.\n",
+ "\n",
+ "\n",
+ "\n",
+ "**Quantum Random Walks**\n",
+ "\n",
+ "\n",
+ "The process of the quantum random walk isn't that much different from its classical counterpart, although \n",
+ "the observed results of the two processes have many differences. First, let us motivate the creation of a \n",
+ "QRW. The idea is that when one performs analysis on a classical random walk, you can find that \n",
+ "$\\sigma^2 \\ \\sim \\ T$, where $\\sigma$ is the standard deviation of the random walk's probability distribution, \n",
+ "and $T$ is the number of time-steps of the random walk. For the quantum random walk, we can see that \n",
+ "$\\sigma^2 \\ \\sim \\ T^2$. In other words, the standard deviation grows at a quadratically faster rate. \n",
+ "At a high level, this signifies that the quantum walker \"spreads out\" quadratically faster than the \n",
+ "classical one, showing that the process of a QRW is quadratically faster than its classical counterpart.\n",
+ "\n",
+ "\n",
+ "In order to create a quantum random walk, we have to translate the components of the classical random walk \n",
+ "to a quantum problem. We can encode the position of a \"walker\" in some $n$ -dimensional space with a vector\n",
+ "$\\lvert j\\rangle$. For the purpose of this project, we will be investigating a very basic case of a \n",
+ "random walk on a ring-shaped graph, with adjacent nodes connected by a single edge. The configuration \n",
+ "looks something like this:\n",
+ "\n",
+ "\n",
+ "\n",
+ "\n",
+ "\n",
+ "Going back to our original idea of some position vector $\\lvert j\\rangle$, it is apparent that in order to \n",
+ "encode the location of a \"walker\" on this graph, we need to assign a specific value of our position vector \n",
+ "to each node. Well, this is fairly simple, for a graph of $K$ nodes, we form a Hilbert space\n",
+ "$H_W$ spanned by the following set:\n",
+ "\n",
+ "\n",
+ "$$H_W \\ = \\ \\{\\lvert j\\rangle \\ : \\ j \\ = \\ 0, \\ ..., \\ K \\ - \\ 1 \\}$$\n",
+ "\n",
+ "\n",
+ "We also require another vector in order to create a random walk. We need a \"coin vector\", which will encode \n",
+ "the direction in which the random walk will progress at the $T$-th step of the process. This Hilbert space \n",
+ "is spanned by the two basis states, representing forward and backward progression on our number-line-like \n",
+ "graph (actually, I guess our graph looks more like a ring, so I guess our two basis states will represent \n",
+ "clockwise and counter-clockwise motion, but it's the same idea). We will call this Hilbert space $H_C$, \n",
+ "and we can again define our spanning set:\n",
+ "\n",
+ "\n",
+ "$$H_C \\ = \\ \\{\\lvert i\\rangle \\ : \\ i \\ = \\ \\downarrow, \\ \\uparrow\\rangle\\}$$\n",
+ "\n",
+ "\n",
+ "Where the upward-arrow symbol represent counter-clockwise motion, and the downward arrow represents \n",
+ "clock-wise motion. Now that we have defined all of the vectors we need to encode the information about \n",
+ "our random walk, we must understand how we can realize these vectors in our quantum algorithm. Well, this is \n",
+ "again fairly simple. For a graph of $K \\ = \\ 2^n$ nodes, we require $n$ qubits to encode binary representations \n",
+ "of numbers ranging from $0$ to $K \\ - \\ 1$, therefore each of the vectors spanning $H_W$ will simply be given \n",
+ "by the binary representation of $j$ corresponding to the basis vector $\\lvert j\\rangle$. For the coin vector, \n",
+ "since we have only two states, we only need one qubit to encode the two possible states:\n",
+ "\n",
+ "\n",
+ "$$\\lvert 0\\rangle \\ = \\ \\lvert \\uparrow\\rangle \\ \\ \\text{and} \\ \\ \\lvert 1\\rangle \\ = \\ \\lvert \\downarrow\\rangle$$\n",
+ "\n",
+ "\n",
+ "In order to represent the total space of all possible states of our system, we take the tensor product of the \n",
+ "two spanning sets, which will then span the new Hilbert space $H_C \\ \\otimes \\ H_W$. We will write a general \n",
+ "element of this Hilbert space as $\\lvert i\\rangle \\ \\otimes \\ \\lvert j\\rangle$.\n",
+ "\n",
+ "Moving right along, we now require a method to evolve our random walk forward at each step. We define a random \n",
+ "walk evolution operator as follows:\n",
+ "\n",
+ "\n",
+ "$$U \\ = \\ \\lvert \\uparrow\\rangle\\langle\\uparrow\\lvert \\ \\otimes \\ \\displaystyle\\sum_{j} \\ \\lvert j \\ + \\ 1\\rangle\\langle j\\lvert \\ + \\ \\lvert \\downarrow\\rangle\\langle\\downarrow\\lvert \\ \\otimes \\ \\displaystyle\\sum_{j} \\ \\lvert j \\ - \\ 1\\rangle\\langle j\\lvert $$\n",
+ "\n",
+ "\n",
+ "By the way, I didn't come up with this genius operator, this came from the paper I referenced at the top of the \n",
+ "post. Essentially, since our qubits take on states $\\lvert 0\\rangle$ and $\\lvert 1\\rangle$, we know that \n",
+ "any possible, general basis state vector formed from qubits $\\lvert n\\rangle^{\\otimes \\ N}$ will be orthogonal to \n",
+ "all other vectors in the basis spanning the space. Because of this, we can create an operator that first \n",
+ "\"picks out\" the coin vector's state (the other term just goes to $0$, as, like I said, the states or orthogonal), \n",
+ "and then sums over all possible position states until it finds the position state to which the operator is \n",
+ "being applied. The inner product of the vector and itself is just one (the vectors are not only orthogonal, \n",
+ "they're orthonormal!), and the new position state of the vector is $\\lvert j \\ \\pm \\ 1\\rangle$, depending on \n",
+ "the state of the coin vector. This did exactly what we wanted, it evolved our random walk either forward or \n",
+ "backwards by one step! If you're still not convinced, let's check to see what happens when we have the state \n",
+ "$\\lvert \\uparrow\\rangle \\ \\otimes \\ \\lvert 1\\rangle$ and we apply the $U$ operator:\n",
+ "\n",
+ "\n",
+ " $$U (\\lvert \\uparrow\\rangle \\ \\otimes \\ \\lvert 1\\rangle) \\ \\ = \\ \\Big( \\ \\lvert \\uparrow\\rangle\\langle\\uparrow\\lvert \\ \\otimes \\ \\displaystyle\\sum_{j} \\ \\lvert j \\ + \\ 1\\rangle\\langle j\\lvert \\ + \\ \\lvert \\downarrow\\rangle\\langle\\downarrow\\lvert \\ \\otimes \\ \\displaystyle\\sum_{j} \\ \\lvert j \\ - \\ 1\\rangle\\langle j\\lvert \\Big )(\\lvert \\uparrow\\rangle \\ \\otimes \\ \\lvert 1\\rangle)$$\n",
+ " \n",
+ " $$\\Rightarrow \\ \\lvert \\uparrow\\rangle\\langle\\uparrow\\lvert \\uparrow\\rangle \\ \\otimes \\ \\displaystyle\\sum_{j} \\ \\lvert j \\ + \\ 1\\rangle\\langle j\\lvert 1\\rangle \\ + \\ \\lvert \\downarrow\\rangle\\langle\\downarrow\\lvert \\uparrow\\rangle \\ \\otimes \\ \\displaystyle\\sum_{j} \\ \\lvert j \\ - \\ 1\\rangle\\langle j\\lvert 1\\rangle$$\n",
+ "\n",
+ "\n",
+ " $$\\Rightarrow \\ \\lvert \\uparrow\\rangle \\ \\otimes \\ \\lvert 2\\rangle \\ + \\ 0\\lvert \\downarrow\\rangle \\ \\otimes \\ \\lvert 0\\rangle \\ = \\ \\lvert \\uparrow\\rangle \\ \\otimes \\ \\lvert 2\\rangle$$\n",
+ "\n",
+ "\n",
+ " As you can see, it works! Now, we must consider the randomness of the random walk. For the purposes of our \n",
+ " random walk, we will set $p_{r} \\ = \\ 0.5$, and therefore make $p_{l} \\ = \\ 0.5$ as well. At each time step, \n",
+ " it is necessary that we randomly flip the state of our coin vector $\\lvert i\\rangle$. The Hadamard \n",
+ " transformation seems like a natural choice, as:\n",
+ "\n",
+ "\n",
+ " $$H \\ = \\ \\frac{1}{\\sqrt{2}}\\begin{pmatrix} 1 && 1 \\\\ 1 && -1 \\end{pmatrix} \\ \\Rightarrow \\ H \\lvert \\uparrow\\rangle \\ = \\ \\frac{\\lvert \\uparrow\\rangle \\ + \\ \\lvert \\downarrow\\rangle }{\\sqrt{2}} \\ \\Rightarrow \\ H \\lvert \\downarrow\\rangle \\ = \\ \\frac{\\lvert \\uparrow\\rangle \\ - \\ \\lvert \\downarrow\\rangle }{\\sqrt{2}}$$\n",
+ "\n",
+ "\n",
+ " The probability of measuring one of the basis states is given by squaring the coefficient in the linear combination, which we can see for both outcomes is equal to $0.5$, the same probability of a step to the \n",
+ " right/step to the left that we originally desired. We can now combine our operators into one \"master operator\" \n",
+ " that works as one complete step of the random walk, including randomizing the coin vector:\n",
+ "\n",
+ "\n",
+ " $$S \\ = \\ U \\ (H \\ \\otimes \\ I)$$\n",
+ "\n",
+ "\n"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "**Tutorial: Building a QRW With Cirq**\n",
+ "\n",
+ "\n",
+ "Now, that we have established all of the necessary mathematical rigour to create a quantum random walk, we \n",
+ "need to translate this into code. We can start by creating a qubit register, which will be used to represent \n",
+ "all of the position vectors on our graph. Recall that for an $N$ qubit register, we can encode all numbers \n",
+ "ranging from $0$ to $2^N \\ - \\ 1$. For now, we will set $N \\ = \\ 7$:"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 2,
+ "metadata": {},
+ "outputs": [
+ {
+ "name": "stdout",
+ "output_type": "stream",
+ "text": [
+ "[cirq.GridQubit(0, 0), cirq.GridQubit(0, 1), cirq.GridQubit(0, 2), cirq.GridQubit(0, 3), cirq.GridQubit(0, 4), cirq.GridQubit(0, 5), cirq.GridQubit(0, 6)]\n"
+ ]
+ }
+ ],
+ "source": [
+ "import cirq\n",
+ "import random\n",
+ "import numpy as np\n",
+ "import copy\n",
+ "import sympy\n",
+ "import itertools\n",
+ "from matplotlib import pyplot as plt\n",
+ "\n",
+ "number_qubits = 7\n",
+ "\n",
+ "qubits = []\n",
+ "for i in range(0, number_qubits):\n",
+ " qubits.append(cirq.GridQubit(0, i))\n",
+ "\n",
+ "print(qubits)"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "Next, we have to initialize our qubit register into some initial state. This can vary quite a bit, depending on \n",
+ "the simulation that we want to make. To start, let's say that our initial position vector for our \"random walker\" \n",
+ "is roughly in the middle of the graph (not exactly, as we have an even number of position vector values). Let's \n",
+ "also say that our coin vector is initialized in the $|\\downarrow\\rangle$ state. Since $|\\downarrow\\rangle$ corresponds to $|1\\rangle$, the only operations that have to be performed in this qubit initialization method is \n",
+ "an $X$ gate acting on ``GridQubit(0, 1)`` (initializing the position vector), as well as an $X$ gate acting on \n",
+ "the coin qubit:"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 3,
+ "metadata": {},
+ "outputs": [],
+ "source": [
+ "def initial_state():\n",
+ "\n",
+ " yield cirq.X.on(cirq.GridQubit(0, 1))\n",
+ " yield cirq.X.on(cirq.GridQubit(0, number_qubits))"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "Now that we have created and initialized our qubit register, we have to create an operation that can evolve \n",
+ "our random walk forward by one step. At a high level, our evolution operation will follow this process:\n",
+ "\n",
+ "1. \"Flip\" the coin qubit. The result of this \"flip\" will tell us in which direction our random walker should move. This \"flip\" operation is nothing more than a Hadamard transformation applied to the coin qubit after each evolution operation.\n",
+ "\n",
+ "\n",
+ "2. Based on the state of the coin qubit after the flip, either perform the operation $|j\\rangle \\ \\rightarrow \\ |j \\ + \\ 1\\rangle$ or $|j\\rangle \\ \\rightarrow \\ |j \\ - \\ 1\\rangle$ on the register of qubits encoding the position vector of the random walker on the graph. This will involve having two operations controlled by opposite states of the coin quibt, each representing a step forward or a step backward on the graph. Thus, our evolution operation will look something like this:\n",
+ "\n",
+ "\n",
+ "\n",
+ "\n",
+ "If we construct our evolution operator in this fashion, the coin qubit is able to dictate whether the walker \n",
+ "steps forwards or backwards without ever having to be measured!\n",
+ "\n",
+ "\n",
+ "Now that we have a high-level setup for our evolution operator, we have to construct the \"step forward\" and \n",
+ "\"step backward\" operations. These are nothing more than an addition and a subtraction operator, each of with \n",
+ "adds or substracts $1$ from the position vector. \n",
+ "\n",
+ "\n",
+ "Before we actually dive into making the addition and substraction operators, it will be useful for us to define \n",
+ "an operation which we will call an n-qubit Toffoli gate. The name is pretty self-explanatory, it is just \n",
+ "an $X$ gate that is controlled by an arbitrary number of qubits $n$, rather than only $1$ or $2$ in the \n",
+ "standard $CNOT$ and Toffoli gates.\n",
+ "\n",
+ "\n",
+ "In order to implement this, we have to use a series of Toffoli gates, along with a collection of ancilla \n",
+ "qubits ($n \\ - \\ 1$) ancilla qubits to be exact:"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 4,
+ "metadata": {},
+ "outputs": [
+ {
+ "name": "stdout",
+ "output_type": "stream",
+ "text": [
+ "[cirq.GridQubit(1, 0), cirq.GridQubit(1, 1), cirq.GridQubit(1, 2), cirq.GridQubit(1, 3), cirq.GridQubit(1, 4), cirq.GridQubit(1, 5), cirq.GridQubit(1, 6)]\n"
+ ]
+ }
+ ],
+ "source": [
+ "ancilla = []\n",
+ "for i in range(0, number_qubits):\n",
+ " ancilla.append(cirq.GridQubit(1, i))\n",
+ "\n",
+ "print(ancilla)"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "We start by applying a Toffoli gate to the first two control qubits, with the target as the first ancilla \n",
+ "qubit. Then, we apply a Toffoli controlled by the third control qubit and the first ancilla qubit, which we \n",
+ "targetted with the previous Toffoli gate. We continue this process until all control qubits have been utilized \n",
+ "in Toffoli gates, and then attach a $CNOT$ gate to our final ancilla qubit, targetting the \"overall\" original \n",
+ "target qubit of the $n$-qubit Toffoli gate. Our final step is to perform an uncomputation operation, \n",
+ "which means that we apply our series of Toffoli gates in reverse. This allows us to revert our ancilla back to \n",
+ "its initial state $|0\\rangle^{\\otimes n \\ - \\ 1}$, thus allowing it to be re-used for future computation.\n",
+ "\n",
+ "\n",
+ "This process may seem a little bit confusing, but here is an example of the generated circuit for the \n",
+ "$n$-qubit Toffoli gate for the case of $n \\ = \\ 4$, when this process is implemented in Cirq:"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 5,
+ "metadata": {},
+ "outputs": [
+ {
+ "name": "stdout",
+ "output_type": "stream",
+ "text": [
+ "(0, 0): ───@───────────────────────@───\n",
+ " │ │\n",
+ "(0, 1): ───@───────────────────────@───\n",
+ " │ │\n",
+ "(0, 2): ───┼───@───────────────@───┼───\n",
+ " │ │ │ │\n",
+ "(0, 3): ───┼───┼───@───────@───┼───┼───\n",
+ " │ │ │ │ │ │\n",
+ "(0, 4): ───┼───┼───┼───X───┼───┼───┼───\n",
+ " │ │ │ │ │ │ │\n",
+ "(1, 0): ───X───@───┼───┼───┼───@───X───\n",
+ " │ │ │ │ │\n",
+ "(1, 1): ───────X───@───┼───@───X───────\n",
+ " │ │ │\n",
+ "(1, 2): ───────────X───@───X───────────\n"
+ ]
+ }
+ ],
+ "source": [
+ "number_qubits = 4\n",
+ "\n",
+ "def apply_n_qubit_tof(ancilla, args):\n",
+ "\n",
+ " if (len(args) == 2):\n",
+ " yield cirq.CNOT.on(args[0], args[1])\n",
+ "\n",
+ " elif (len(args) == 3):\n",
+ " yield cirq.CCX.on(args[0], args[1], args[2])\n",
+ "\n",
+ " else:\n",
+ "\n",
+ " yield cirq.CCX.on(args[0], args[1], ancilla[0])\n",
+ " for k in range(2, len(args)-1):\n",
+ " yield cirq.CCX(args[k], ancilla[k-2], ancilla[k-1])\n",
+ "\n",
+ " yield cirq.CNOT.on(ancilla[len(args)-3], args[len(args)-1])\n",
+ "\n",
+ " for k in range(len(args)-2, 1, -1):\n",
+ " yield cirq.CCX(args[k], ancilla[k-2], ancilla[k-1])\n",
+ " yield cirq.CCX.on(args[0], args[1], ancilla[0])\n",
+ "\n",
+ "\n",
+ "control = [cirq.GridQubit(0, i) for i in range(0, number_qubits+1)]\n",
+ "circuit = cirq.Circuit()\n",
+ "circuit.append(apply_n_qubit_tof(ancilla, control))\n",
+ "print(circuit)"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "The reason why I have introduced an extra qubit is because the way that I coded this function takes the last entry \n",
+ "in the ``args`` list as the target qubit, thus I needed $4$ control qubits, plus $1$ target qubit for a total \n",
+ "of $5$ qubits in the ``control`` list (even though one of them is actually the target!)."
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "Now we can get back to creating the addition and substraction operators. Starting with the addition operator, \n",
+ "the idea is:\n",
+ "\n",
+ "\n",
+ "\n",
+ "1. Have a $CNOT$ gate controlled by the coin qubit targetting the least significant qubit. This means that if the coin qubit is in the \"move forward\" state, the addition operator will be activated.\n",
+ "\n",
+ "\n",
+ "2. Apply an $X$ gate to the qubit that was just targetted by the $CNOT$ gate.\n",
+ "\n",
+ "\n",
+ "3. Apply a Toffoli gate controlled by the coin qubit and the qubit on which the $X$ gate was just placed, targetting the second least-significant qubit. This acts as a \"carry operation\", meaning that if the coin qubit is in the addition state, and the least significant qubit is in the $|0\\rangle$ state (meaning it was in the $|1\\rangle$ state, but had the $CNOT$ operation applied to it, we had to apply the $X$ gate to flip it back to the $|1\\rangle$ state so it can activate the Toffoli gate), then flip the value of the next qubit, signifying that the addition mod $2$ carried over a one to the next digit of the number.\n",
+ "\n",
+ "\n",
+ "4. Continue this process with $n$-qubit Toffoli gates controlled by all qubits less significant than the target qubit, along with the coin qubit until all qubits have had Toffoli gates applied.\n",
+ "\n",
+ "\n",
+ "5. Apply $X$ gates to all qubits in the position vector register, as they all had $X$ gates applied to them in the process of addition.\n",
+ "\n",
+ "For the subtraction operator, we can make use of the fact that quantum operations are reversible, meaning that if \n",
+ "we have some addition unitary $A$, such that $A |j\\rangle \\ = \\ |j \\ + \\ 1\\rangle$, then:\n",
+ "\n",
+ "\n",
+ "$$A^{\\dagger}A |j\\rangle \\ = \\ A^{\\dagger}|j \\ + \\ 1\\rangle \\ \\Rightarrow \\ A^{\\dagger}|j \\ + \\ 1\\rangle \\ = \\ |j\\rangle \\ \\Rightarrow \\ A^{\\dagger}|k\\rangle \\ = \\ |k \\ - \\ 1\\rangle$$\n",
+ "\n",
+ "\n",
+ "And so this means that $S \\ = \\ A^{\\dagger}$. Since we can decompose $A$ into a product of a bunch of unitaries, \n",
+ "we get:\n",
+ "\n",
+ "\n",
+ " $$A \\ = \\ U_1 U_2 \\ ... \\ U_n \\ \\Rightarrow \\ S \\ = \\ A^{\\dagger} \\ = \\ U_n^{\\dagger} U_{n - 1}^{\\dagger} \\ ... \\ U_{1}^{\\dagger}$$\n",
+ "\n",
+ "\n",
+ "But our method only uses $X$ gates and controlled $X$ gates, all of which are Hermitian, thus we have:\n",
+ "\n",
+ "\n",
+ "$$S \\ = \\ U_n^{\\dagger} U_{n - 1}^{\\dagger} \\ ... \\ U_{1}^{\\dagger} \\ = \\ U_n U_{n - 1} \\ ... \\ U_{1}$$\n",
+ "\n",
+ "\n",
+ "So basically, our subtraction operation will just be applying our addition operator, but with the order of \n",
+ "gates reversed. This allows us to create one general \"evolution operation\" for our random walk, which adds \n",
+ "or substract $1$ to the random walkers position vector, based on the coin qubit:"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 13,
+ "metadata": {},
+ "outputs": [],
+ "source": [
+ "def walk_step():\n",
+ "\n",
+ " #\"Flip\" the coin vector\n",
+ "\n",
+ " yield cirq.H.on(cirq.GridQubit(0, number_qubits))\n",
+ "\n",
+ " #Implement the Addition Operator\n",
+ "\n",
+ " yield cirq.X.on(cirq.GridQubit(0, number_qubits))\n",
+ "\n",
+ " for i in range(number_qubits, 0, -1):\n",
+ "\n",
+ " yield apply_n_qubit_tof(ancilla, [cirq.GridQubit(0, v) for v in range(number_qubits, i-2, -1)])\n",
+ " yield cirq.X.on(cirq.GridQubit(0, i-1))\n",
+ "\n",
+ " for i in range(number_qubits, 0, -1):\n",
+ " yield cirq.X.on(cirq.GridQubit(0, i-1))\n",
+ "\n",
+ " yield cirq.X.on(cirq.GridQubit(0, number_qubits))\n",
+ "\n",
+ " #Implement the Substraction Operator\n",
+ "\n",
+ " for i in range(number_qubits, 0, -1):\n",
+ " yield cirq.X.on(cirq.GridQubit(0, i-1))\n",
+ "\n",
+ " for i in range(1, number_qubits+1):\n",
+ "\n",
+ " yield apply_n_qubit_tof(ancilla, [cirq.GridQubit(0, v) for v in range(number_qubits, i-2, -1)])\n",
+ " yield cirq.X.on(cirq.GridQubit(0, i-1))"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "Next, we have to append these operations to our quantum circuit, specifically iteratively apply the \n",
+ "``walk_step()`` function in order to evolve our random walk forward. After we do this, we measure of position \n",
+ "vector qubit register, by applying measurement gates, and we sample our circuit repeatedly. In code, for the \n",
+ "example of $10$ iteration of our evolution operator, $200$ samples of the circuit, and $7$ position vector \n",
+ "qubits, we have:"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 7,
+ "metadata": {},
+ "outputs": [
+ {
+ "name": "stdout",
+ "output_type": "stream",
+ "text": [
+ "Counter({12: 50, 14: 24, 20: 16, 10: 15, 16: 13, 52: 12, 42: 8, 22: 7, 34: 7, 24: 6, 48: 5, 32: 5, 30: 4, 54: 4, 40: 4, 36: 4, 38: 4, 18: 3, 46: 3, 26: 3, 44: 2, 50: 1})\n"
+ ]
+ }
+ ],
+ "source": [
+ "number_qubits = 7\n",
+ "iterator = 30\n",
+ "sample_number = 200\n",
+ "\n",
+ "circuit = cirq.Circuit()\n",
+ "\n",
+ "circuit.append(initial_state())\n",
+ "\n",
+ "for j in range(0, iterator):\n",
+ " circuit.append(walk_step())\n",
+ "circuit.append(cirq.measure(*qubits, key='x'))\n",
+ "\n",
+ "simulator = cirq.Simulator()\n",
+ "result = simulator.run(circuit, repetitions=sample_number)\n",
+ "final = result.histogram(key='x')\n",
+ "\n",
+ "print(final)"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "Finally, we then graph the results of our simulation, with final position vector value on the x-axis and the \n",
+ "number of occurences of that position vector value on the y-axis. This gives us a probability distribution for \n",
+ "the position of the random walker. It is important to note that the graphs will only have either even or odd \n",
+ "numbered data point, depending on the initial position of the walker and the number of steps taken:"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 8,
+ "metadata": {},
+ "outputs": [
+ {
+ "data": {
+ "image/png": "iVBORw0KGgoAAAANSUhEUgAAAXQAAAD8CAYAAABn919SAAAABHNCSVQICAgIfAhkiAAAAAlwSFlzAAALEgAACxIB0t1+/AAAADl0RVh0U29mdHdhcmUAbWF0cGxvdGxpYiB2ZXJzaW9uIDIuMi40LCBodHRwOi8vbWF0cGxvdGxpYi5vcmcv7US4rQAAIABJREFUeJzt3Xl4VGWWP/Dvqcoesm9kJREQCSIgQdFgt4KAK+LSaq+M3dN2jzNj+3S3Nkz//PV0T3eL44y9zOhMM+pILzOuCC5oQMAFFDHshMWEnUBSCSFUIKlKqvLOH1UVKqEqqUrdWu7N9/M8PEnd1PLmJnV4c+55zytKKRARkf6Zoj0AIiLSBgM6EZFBMKATERkEAzoRkUEwoBMRGQQDOhGRQTCgExEZBAM6EZFBMKATERlEXCRfLDc3V5WXl0fyJYmIdG/r1q2tSqm8oe4X0YBeXl6O2traSL4kEZHuicjRQO7HlAsRkUEwoBMRGQQDOhGRQTCgExEZBAM6EZFBMKATERkEAzoRkUEEVIcuIkcAdABwAnAopapEJBvAywDKARwBcK9S6kx4hklEREMJZoZ+g1JqqlKqyn17MYB1SqnxANa5b8ekldsbUb10PSoWv4PqpeuxcntjtIdERKS5UFIudwBY7v58OYCFoQ9Heyu3N2LJit1obO+CAtDY3oUlK3YzqBOR4QQa0BWANSKyVUQedB8rUEqdcn/eBKBA89Fp4KmaA+jqcfY71tXjxFM1B6I0IiKi8Ai0l8sspVSjiOQDWCsi+72/qJRSIqJ8PdD9H8CDAFBWVhbSYIfjZHtXUMeJiPQqoBm6UqrR/dEC4A0AVwFoFpFCAHB/tPh57DKlVJVSqiovb8hmYZorykwO6jgRkV4NGdBFJFVE0jyfA5gHYA+ANwEsct9tEYBV4RpkKB6dPwHxJul3LDnejEfnT4jSiIiIwiOQGXoBgI0ishPAFgDvKKXeA7AUwFwRqQdwo/t2zFk4rRjXXXrhL4PizGQ8cddkLJxWHMVRERFpb8gculLqEIApPo6fBjAnHIPSWkZyPACgMCMJmxbPjvJoiIjCY0SsFLV02AAATVYbbAMqXoiIjGJkBHSrHSYBlHLVoRMRGdGICOjNVhsmFqYDAI6d7ozyaIiIwsPwAd3W44TV5kDVmCwAwLE2BnQiMibDB3SL1Q4AqCxKR3K8mQGdiAzL+AHdfUG0ID0JZdkpDOhEZFgjIKC7Zuj5aUkozU7BcQZ0IjIowwf0Zqtrhp6fntg3Q1fKZ9sZIiJdM3xAt3TYEWcSZKckoCw7GZ3dTpw+3x3tYRERac74Ad1qR15aIkwmQVlOCgBWuhCRMRk/oHfYkJ+WCAAoy3YHdNaiE5EBGT+gW+3IT08CAJRkcYZORMZl/IDuNUNPijejID2RAZ2IDMnQAd3ucOJMZw/y05L6jrEWnYiMytABvcVdg16Qnth3rCw7lbXoRGRIhg7ofYuK+gX0FLbRJSJDMnZA9ywq8k655CSzjS4RGZKxA7qfGTrAShciMh5jB3T3xhY5qRcCeqk7oDOPTkRGY+iA3my1IS8tEWaT9B3LG5WIpHgTjnJxEREZjKEDuqXD3i9/DgAiwtJFIjKkERDQEy86XsY2ukRkQMYO6FZb37J/b6Vso0tEBmTYgN7j7MXp890+Z+hjslPYRpeIDMewAb313MUlix5so0tERmTYgN7s3hy6IO3ilEsZSxeJyIAMG9AtXlvPDdTXRpeli0RkIMYN6F6bQw/kaaN7lDN0IjIQ4wZ0qw0iQO6oBJ9fZy06ERmNcQN6hx05qYmIM/v+FktZi05EBmPogO6rZNGDbXSJyGgCDugiYhaR7SLytvt2hYh8JiINIvKyiPjObURJs9XWb2OLgcqyU9hGl4gMJZgZ+g8A7PO6/SSA3yilxgE4A+A7Wg4sVL76uHgbw1p0IjKYgAK6iJQAuBXAc+7bAmA2gNfcd1kOYGE4BjgcDmcvWs/ZfZYserCNLhEZTaAz9N8CeAxAr/t2DoB2pZTDffsEgGJfDxSRB0WkVkRqW1paQhpsoE6f74ZS8NnHxcPTRpe16ERkFEMGdBG5DYBFKbV1OC+glFqmlKpSSlXl5eUN5ymCZrF6atD9z9DZRpeIjCYugPtUA1ggIrcASAKQDuB3ADJFJM49Sy8B0Bi+YQan2b1KtGCQGTrAWnQiMpYhZ+hKqSVKqRKlVDmA+wGsV0p9HcAGAPe477YIwKqwjTJIF1aJ+p+hA2yjS0TGEkod+k8A/FBEGuDKqT+vzZBCZ+lwzdBzRw0e0MvYRpeIDCSQlEsfpdQHAD5wf34IwFXaDyl0zVY7clITkBA3+P9Xnq6Lx9o6hwz+RESxzpArRVs6XJtDD4VtdInISAwZ0C0d9kFLFj08tegsXSQiIzBkQG+22lAQwAzd00aXlS5EZASGC+jOXoXWc92DrhL1xtJFIjIKwwX0tvPdcPaqQfu4eCtlQCcigzBcQL+wqCjwGTrb6BKRERguoLe4FxXlBThDZxtdIjIKwwV0z6KioVaJenjXohMR6ZnhAnqzpzFXECkXgLXoRKR/hgvolg4bMlPikRhnDuj+eWlso0tExmC8gG4dfC/RgdhGl4iMwnABvbnDPmTb3IEY0InICAwX0FusgfVx8VaanYLjbKNLRDpnqIDe26vQcm7wzaF9KctOwXm20SUinTNUQD/T2Y0epwp4UZEHSxeJyAgMFdAv7FQU/AwdYOkiEembIQN6sDP0kiy20SUi/TNUQPf0cQl2hp6cYEZ+GtvoEpG+GSqge/q4BLpK1BtLF4lI7wwV0C1WG9KT4pAUH9gqUW9lOSnMoRORrhkqoDdbA9t6zpey7BScstpgd7CNLhHpk6ECuqXDFtSyf2+eNronzrCNLhHpk6ECerM1+GX/HqxFJyK9M0xAV0qhpSO4xlzeWItORHpnmIB+tqsH3c7eoPu4eOSlJSIxjm10iUi/DBPQPRtbDDflwja6RKR3hgnowW495wsDOhHpmXECet/Wc8OboQNso0tE+maYgN6swQx9TI6rjW4b2+gSkQ4ZJqBbrHaMSoxDamLcsJ/DU+lylGkXItKhIQO6iCSJyBYR2SkidSLyc/fxChH5TEQaRORlEUkI/3D9C6Vk0YOli0SkZ4HM0O0AZiulpgCYCuAmEZkJ4EkAv1FKjQNwBsB3wjfMoTVbbcNqyuWNbXSJSM+GDOjK5Zz7Zrz7nwIwG8Br7uPLASwMywgDZOkIfuu5gdhGl4j0LKAcuoiYRWQHAAuAtQAOAmhXSjncdzkBoNjPYx8UkVoRqW1padFizBdRSoXUx8UbSxeJSK8CCuhKKadSaiqAEgBXAbgs0BdQSi1TSlUppary8vKGOczBWW0O2Hp6h72oyFtZNtvoEpE+BVXlopRqB7ABwDUAMkXEU1JSAqBR47EFrMVTshhiDh1w1aKzjS4R6VEgVS55IpLp/jwZwFwA++AK7Pe477YIwKpwDXIofYuKQsyhAxfa6DayjS4R6UwgM/RCABtEZBeAzwGsVUq9DeAnAH4oIg0AcgA8H75hDq5Zwxn6mBy20SUifRpyFY5SaheAaT6OH4Irnx51F2bo2lwUBRjQiUh/DLFS1NJhR0qCGaNCWCXqwTa6RKRXhgjozVZXyaKIhPxcbKNLRHpliICuxaIibwzoRKRHhgjoLR12TS6IerCNLhHpkSECuivlou0MnW10iUhvdB/Qz9kd6Ox2ajpDZ6ULEemR7gO6xeqqQS/QMqCzFp2IdEj3Ab1Zw1WiHqVso0tEOqT7gK7F5tADsY0uEemR7gN6S0fom0P7wtJFItIb3Qf0ZqsNiXEmpCeFvkrUG9voEpHe6D6gW9w16FqsEvXGNrpEpDf6D+hWOwo0vCDqwTa6RKQ3ug/ozR2hbw7tC0sXiUhvdB/QW6za9nHx8CwuYh6diPRC1wG9s9uBDrsjLDP0TQ2tAIDHV9Wheul6rNwetR32iIgCouuAruXWc95Wbm/ET9/Y03e7sb0LS1bsZlAnopim74DurkHXctk/ADxVcwBdPf2rW7p6nHiq5oCmr0NEpCVdB/Rmq2eVqLYz9JPtvitb/B0nIooFug7onhm6lsv+AaAoMzmo40REsUDnAd2GBLMJmSnxmj7vo/MnIDne3O9YcrwZj86foOnrEBFpSdv18hFmsdqRp9Feot4WTisG4MqlN7rTLD+7vbLvOBFRLNL9DD0cJYuAK6hvWjwbr37/GgBAaqKu/+8johFA3wE9TMv+vV1ZloWc1ASs2dsc1tchIgqVrgN6szV8M3QPs0kwt7IAG/Zb2KiLiGKabgO6rccJq82heYWLL/MnjcY5uwOfHDwd9tciIhou3Qb0cG1s4cs1Y3OQmmDGmjqmXYgoduk2oF9YVBT+GXpSvBnXX5aPtXub4exVYX89IqLh0G1Av7CoKPwzdACYV1mA1nN27Dh+JiKvR0QULP0GdPcMXes+Lv7ccFk+4s2CGqZdiChGDRnQRaRURDaIyF4RqRORH7iPZ4vIWhGpd3/MCv9wL2jusCPOJMhKSYjI66UnxePasbmoqWuCUky7EFHsCWSG7gDwI6VUJYCZAP5WRCoBLAawTik1HsA69+2I8awSNZm0XSU6mHmTCnD0dCe+aD4XsdckIgrUkAFdKXVKKbXN/XkHgH0AigHcAWC5+27LASwM1yB9ca0SjUz+3GNuZQFEgJq6poi+LhFRIILKoYtIOYBpAD4DUKCUOuX+UhOAAk1HNgSL1R6RChdv+WlJuLIsiwGdiGJSwAFdREYBeB3AI0opq/fXlCup7DOxLCIPikitiNS2tLSENFhvlg5bxC6IeptXWYC6k1acOMO9RokotgQU0EUkHq5g/hel1Ar34WYRKXR/vRCAxddjlVLLlFJVSqmqvLw8LcYMu8OJM509EStZ9DZ/0mgA4CIjIoo5gVS5CIDnAexTSj3t9aU3ASxyf74IwCrth+dbS5g2tghEeW4qJhSkMe1CRDEnkBl6NYBvApgtIjvc/24BsBTAXBGpB3Cj+3ZEXNhLNPIzdMBV7fL5kTa0ne+OyusTEfkyZJNvpdRGAP5qA+doO5zAWKyugJ4XhRk64Eq7/Nv6Bry/rxn3VpVGZQxERAPpcqWopcPdxyUKF0UBYFJROoozk5lHJ6KYos+AbrXDbBLkpEYnoIu4eqR/XN+Czm5HVMZARDSQPgN6hw25oxJgjuAq0YHmTxoNu6MXHx7QrhSTiCgUugzozVZ7VEoWvc0oz0JWSjy3piOimKHLgG7psEdlUZG3OLMJcyYWYN2+ZvQ4e6M6FiIiQK8B3WpDXpRn6IAr7WK1ObD5ELemI6Lo011A73H24vT57qgsKhrouvG5SI7n1nREFBt0F9Bbz0V3UZG3pHgzvnxpHtbsbUJvFLamW7m9EdVL16Ni8TuoXroeK7c3RnwMRBQ7dBfQm63RW/bvy/zLC9BstWPnifaIvu7K7Y1YsmI3Gtu7oAA0tndhyYrdDOpEI5juArpn67loLSoaaPaEAsSZJOLVLk/VHEBXj7Pfsa4eJ56qORDRcRBR7NBfQI9yH5eBMlLiMfOSnIg36zrZ3hXUcSIyPl0F9JXbG/Hku/sBAHc+sylm0gvzJxXgUMt5NFgitzVdUWZyUMeJyPh0E9A9OeMOu2up/cmztpjJGc+tdPVIj+Qs/dH5ExA3YKVscrwZj86fELExEFFs0U1Aj+Wc8eiMJEwpzcSaCAb0hdOKkZ+WiMQ414/QbBL86s7LsXBaccTGQESxRTcBPdZzxvMnFWDnibM4dTYy42npsOPkWRsenjMev71vKpy9CoUZTLcQjWS6CeixnjOe5067rI1QtcsnB1sBuBY33XT5aKQlxeGV2uMReW0iik26CeiPzp+A5Hhzv2OxlDMelz8KY/NSI5ZH31jfiozkeEwqykBSvBl3TC3C6t2nYLX1ROT1iSj26CagL5xWjCfumozizGQIgOLMZDxx1+SYyhnPmzQamw+14WxneIOqUgqbGlpx7dicvhbC91aVwu7oxZs7Tob1tYkodg25BV0sWTitOKYC+EDzJ43Gf3xwEOv2N+OuK0vC9jqHW8/j5FkbHroht+/Y5OIMXDY6Da/WHsc3Zo4J22sTUezSzQxdD64ozkBGcjz+4Y3dYe2vsqnBlT+fNe5CQBcR3FtVip0nzmJ/k1Xz1ySi2MeArqE3d57EObsDtp7esPZX+bi+FSVZyRiTk9Lv+J3TipFgNuGVz09o+npEpA8M6Bp6quYAnAO6LmpdK+9w9uLTQ6cxa1wuRPovLMpKTcDcygK8sf0E7A6nn2cgIqNiQNdQJGrldzeeRYfNgWqvdIu3e2eU4kxnD9bts2j2mkSkDwzoGopErbwnf37t2ByfX581LhdFGUl4+XPWpBOFSm97DjCgaygStfIf17diUlE6ckb5bh9sNgnumV6Cj+pbYmYVLZEe6XHPAQZ0DXlq5YsyXK19k+JNmtbKd3Y7sO3YmX7VLb58paoUSgGvb+XFUaLhiuX+Uf4woGts4bRifLJkDr5dXYHeXuCGy/I1e+4th9vQ41R+8+cepdkpuHZsDl7ZejwqW+MRGUGs94/yhQE9TBZMLUK3s1fTVgCbGlqRYDZhRnn2kPe9b0Ypjrd1YfPh05q9PtFIEuv9o3xhQA+TKSUZGJOTgrd2arcU/+P6VlSVZyE5wTzkfedPcjfs4sVRomF5dP4EDNhyAElxppjpH+ULA3qYiAhuv6IImxpa0XrOHvLztXTYsb+pY8h0i0dSvBkLpxbj3T1NONvFhl1EwZpbWQCTCFITL0ygvj2rIqbbjwwZ0EXkBRGxiMger2PZIrJWROrdH7PCO0x9un1KEXoVsHr3qZCfy9Mud6gLot76GnZp+FcC0Ujx4RctcPQqPL9oBvb/003ITk3AF82R22ZyOAKZob8I4KYBxxYDWKeUGg9gnfs2DTBhdBomFKRp0gFxU4OrXe7lxRkBP+by4nRMLExn2oVoGGrqmpCdmoAZ5dlIijfja1eVYd3+Zhw9fT7aQ/NryICulPoIQNuAw3cAWO7+fDmAhRqPyzAWTC1C7dEzaAzhyrhSChvr+7fLDYSrYVcJdjeexd6TbNhFFKhuRy/W77fgxon5fe+5b14zBmYRLP/kaJRH599wc+gFSilPHqEJQIFG4zGc264oBAC8HULaw9MuN9D8ubeFU90Nu7ibEVHANh86jQ6bo28nMgAoSE/CLZML8WrtcZxzb1Yfa0K+KKqUUgD8FjuLyIMiUisitS0tLaG+nO6MyUnFlNLMkPLYvtrlBiorNQHzJhVg5Y5GNuwiClBNXRNSEsyYNb7/e+6B6nJ02B14LUYnSMMN6M0iUggA7o9+O0EppZYppaqUUlV5eXnDfDl9WzClCHUnrTjYMrwLKhsbWlGceXG73EDdW1WK9s6eiO13SqRnvb0Ka/c24/oJeUga0MpjWlkWppZmYvmnR2Ny0d5wA/qbABa5P18EYJU2wzGm264ohAiGVZPucPbik4O+2+UGqnpcLoozk/FKLVsBEA1lx4l2WDrs/dIt3h6oLsfh1vP48IvYyzgEUrb4vwA+BTBBRE6IyHcALAUwV0TqAdzovk1+FKQn4eqKbLy58yRcGarAedrlDvzTLxhmk+Du6SX4uL4lpIuzRCNBTV0T4kzit23HLZMLUZCeiBc2HY7wyIYWSJXLV5VShUqpeKVUiVLqeaXUaaXUHKXUeKXUjUqpgVUwNMCCKcU41HIedUFWmwzVLjdQX5leAqWA1zhLJ/JLKYU1dc24ZmwOMpLjfd4n3mzCN2eOwcf1rWiwdER4hIPjStEIufny0YgzCd7aFVzaZWNDKyoL/bfLDVRpdgqqx+XgVTbsokHorf+31hos53C49TzmTfKdbvH46lVlSIgz4b83HYnMwALEgB4hWakJuG58Lt7eeSrggNrZ7cC2o+0hpVu83VtVihNnuvDpITbsoovpsf+31ta4CwfmVQ5eiZ0zKhF3TCnCim2NONsZO601GNAjaMHUIjS2d2HbsTMB3X/L4TZ0O3uHVa7oy/xJo5GeFMeadPJJj/2/tVZT14SppZkoSE8a8r4PVFegq8eJlz4/FoGRBYYBPYLmVo5GYpwp4GqXYNrlBiIp3oyF09wNu2JoVkGxwd8F81ju/62lk+1d2HXiLOYPkW7xqCxKx9UV2fjjp0fhcPaGeXSBYUCPoFGJcbhxYgHe2X0qoF+AjQ2nMX1MYO1yA5U3KhHdjl5M+cWaEZkj1YrRcs1KKaT6+T2L5f7fWvKs05g/KfCF7w9UV6CxvQvv74uNNR4M6BF2+5RCtJ7rHjKP3XrOjn2nrJrlzwFXEHr2g4N9t0dijlQLRsw1P7/xMM53OxE3oFeQWSSm+39rqaauCePyR+GSvFEBP2ZuZQFKspLxQoxcHGVAj7DrJ+QjLTFuyA6MoSz398dfjvQf36pDS0foPdtHiqXv7jdUrvnd3afwq9X7cMvk0fjne65AcWYyBEBqohm9SmFcfuABTq/OnO/GZ4fbgpqdA641HouuKceWw22oO3k2TKMLHAN6hCXFmzFv0mi8V9c0aG+VTQ2tSE+KC6pd7lD85ULbO3sw41fvY8G/b8TTaw5g27EzcA6oxDFaimE47A4n/vDhQTRZbT6/rsdc87ZjZ/DIyzswrTQTT987FXddWYJNi2fj8NJb8cniOchKTcAv3tob9II4vVm/3wJnr/K7OnQw984oRUqCOSZKGBnQo+D2KYXosDnw4QHfS4cvtMvNDapd7lD85ULzRiXix/MuRbzZhH/f0IC7nv0EVb9ci0de2o5VOxrxl81HDZdiCIZSCu/vbcb833yEJ97dj6Q432+b7NSECI8sNEdPn8d3l9eiID0J//Wtqov6lmQkx+PH8yZgy5E2vKPBJi2xrKauCYUZSbiiJPgJVEZyPO6+sgRv7jipye5koWBAj4LqcbnITk3w24HxyOlOV7tcDfPngGuPxOQBb9rkeDN+eutE/N3s8Xj9b67Ftsfn4vdfnYYbJuTjo/pW/OClHfjpyj2GSjEEo765A996YQv++o+1MJsELz4wA0vvvuKi8ygAznR248+bY7dXtrf2zm488OLncCqFFx+Y4Xfh2n0zSjGxMB1PrN4PW48xu3V2dTvxUX0L5lUWDLtf0qJry9Ht7MX/fBbdEsa4qL76CBVvNuGWyaPx+tZGdHY7kJLQ/8ewsd41c79Ow/w5gL69EJ+qOYCT7V0oykzGo/Mn9NsjMTMlAQumFGHBlCL09irsajyLhc9s8vl8ekwxBKq9sxu/fb8ef9p8FKkJZvzs9kp8Y+YYxJsvzIG8z+PDs8fhvbom/L+Ve3C8rRM/uekymDT860pLdocTD/5pK060deHPf331oBcBzSbBz26vxP3LNmPZR4fw8JzxERxpZHxU3wJbT++Qq0MHMy5/FL50aR7+tPkovv/lsUjw81dcuDGgR8mCKcX48+ZjWLu3GXdM7b/pbKjtcgezcFpxwJvcmkyCqaWZKM5M9lmjbIRytpXbG/sF5h/OvRSd3Q7869ovYO3qwdeuLsMP5064KJ3i6zzePb0E//hWHf7w0SEcP9OJp++delEaI9qUUnjstV3YcrgNv7t/Kq6qGHqNw8xLcnDL5NF49oMG3DO9JOo/94E/s4GTkmDV1DUhIzk+oHMxmAeqy/HAf3+Od/ecuug9HSlMuURJ1ZgsFGYkXbTIyNmrQm6XqzVfqRoAmFycoeuLZb7KD3/86k48vqoOE0en452Hr8MvF04OODceZzbhn+64HD+9ZSLe3dOEr/3XZpyOck51oKfXfoFVO07i0fkTggo6S26eiF4FPPne/jCObmhal4z2OHuxbp8Fcybm9/vrazi+PD4Pl+SmRrWEkQE9SkwmwW1XFOLDL1rQ3tndd9zTLlfr/HkoFk4rxhN3Te4rZyvKSMJV5dl4r64JP3p1J7odsbFKLli+yjgVgOyUBPzPd6/GxML0oJ9TRPDdL12CZ792JepOWnHns58Me2MTrb3y+XH82/oG3FdVioeuHxvUY0uzU/C9L12CVTtOovZI9Jqrat2e4PPDbTjb1TOs6paBTCbBX1WXY+fx9oDbe2iNAT2KFkwpRo9Toaauqe+YJ39eHWK7XK0tnFZ8oZxtyRy8/L2Z+OHcS7FiWyMWvbBFV60EWs/ZsWLbCb9L3c90dof819HNkwvxvw/OxHm7A3c9+wk+i3JDtI31rfiHN3bjuvG5+OWdlw/r+/ub68didHoSfv7W3qh17NS6PUFNXROS4k348qXa7KZ295UlSEuKi1oJI3PoUXR5cTrKc1Lw5s6TuG9GGQDt2uWGm4jg4TnjUZqdjMde24W7//MT/PdfzUBptvZ5/0D5y616Lu5u2G/BBwcs2NV4FkoBJgF8xSWtcsRXlmXhjYeq8VcvbsE3n9+C+2aUYv1+S9C53+HkjL0fk5eWCKutB+PyR+GZr1857NRCSkIcFt98GR55eQde33YCX6kqHdbzDMeps1148l3/6Z7h/MyUUliztxlfGp+nWXuN1MQ4TC/Lwls7T+KtnSdRrEGOPxicoUeRiGDBlCJ8evA0LB02zdvlRsKd00rwx29fDYvVhjuf3YQdx9ujMg5fudVHX9uJe/7jE8z41ftY+Mwm/H59PcwmwQ9vvBRv//0s/MtXpvgs49RyqXtZTgpW/M21KM1Oxp82Hw069zucnPHAx1g67LD19OK+GaVIT/K9aUOg7phahCvLMvHkewfQYQv/X2W2Hid+v64es//lQ6ze04R5lQUXrQMwi+DH8y4N+rl3N57FqbO2kKpbBlq5vbFfW49Ir9ngDD3KFkwtwu/XN2D1rlOoyBuFbmcvqjUuVwy3a8bmYMVD1+KBFz/H/cs+xe/unxZwxzotnLM78Kt39l2UW+1xKmw7dgYLphThhsvycd34vH4XOC8vzoBJRNOKCV8yUxLQ1X1xDXdXjxOPr9qDo6c7/T72uY2HfOaMB3ucr8cAwHMfH8YD1RVBjr4/EcHPbp+EO57ZhGc2HMTimy8L6fn8UUph9e4m/Hr1PjS2d+GWyaOx5OaJKM1O6ffXx6ikOHTYHDh+JviUS01dE8wmwRw/W80Nx1M1B2AfcE3Jk+PZMrIPAAAJpElEQVSPxCydAT3KxuWnYWJhOt7ceRLTx2QhwWzCVRq1y42kcflpeOOhanxneS2+/+etePzWSnx7VmjBw1tntwNHWjtx5PR517/W8zjS2onDp88P2oemVwG/vX+a368HU8YZilNnfbcL6LA58Jv3vwj6+YbzOK3WDUwpzcQ900vwwsbDuH9GKcpzUzV5Xo89jWfxi7f2YsuRNkwsTMe/3jsFMy+5cE3J+2emlMKPXt2Jp9d+gdLsZNw5rSTg11lT14yryrORpeEKX3/nOFJrNhjQY8DYvFS8vesUth1rR0KcCTV1TRHLuWkpd1QiXvruTDzy8nb84u29ONbWiSuKM/Cva78IaAZs63Hi6OlOHG69ELQ9nzdb+wftvLREVOSk4vpL81Cem4rnPz6MNq9qIY/iGKmVL/JXy5+RhI0/me33cbOeXI+TPv4zGOxxfh+j4bl4bP6EvqZe//WtqmE9x8BrA9//8iXYe8qKlz4/jqyUBPz6zsm4b0bpoO0vRARL77oCp9pteOy1XSjMSO4X/P051HIO9ZZz+PrVZcMauz9+f84R+j1kQI+yldsb+/owA0C3oxdLVuwGAF0G9eQEM579+nQ8sXofntt4uN+Fx8b2Lix+fRearDaMzRvlCth9s+3zOGW1wbusPSc1AeW5qZg1Lg8VuSkoz01FeU4qynNTMSqx/69ucWYylqzY3S/VoHU+PBSPzp/gc3yPDbGi9LGbLgv6cf4eo+W5yE9Pwt/OHod/fu8APq5vwXXjg6sS8eT5PWNsbO/C46vqYBLg29UVeHjOeL+bNA+UEGfCf35jOu7+z0/w4B9rseKhazEuP23Qx9TUubea0zg16O/nHKnfQ4nkwpCqqipVW1sbsdfTg+ql633+j16cmYxNi/3P3PRgys/X4GzX4BfOMlPiUZ6Tioq+YJ2CitxUjMlJDfgN7aH1CkKtDXd8oVa5hOtc2HqcmPebj5AUb8Lqh69DXBDVM/5+7/PTErHlpzcOazzH2zpx57ObkBRvxhsPVSMvzX+l2J3PboLDqfDW388a1msNJhznXkS2KqWG/FOIAT3KKha/A18/AQFweOmtkR6Opvx9bwDwxkPXoiI3FZkp+upQSP3V1DXhe3/ail/cMQnfuqZ80Pt2O3pRe7QNHxxowbKPDvm8T6i/9zuPt+O+ZZ9iwuh0vPTdmT7LEZutNlz963X48bxL8Xez9dGbJtCAzpRLlEU75xZO/r634sxkTCvLisKISGvzKgtQPS4HS9/dj2c3HESz1dZvVtpsteGDAxZs2N+CjQ2tOGd3IN4sSIwzXVQNAoT+ez+lNBO/v38avvfnrXjk5e149uvTL8rBr+nbai5ylViRwjr0KPPX0jZWcr+hMPL3Ri4iglljc9HZ7UST1davJ0710vW4+tfr8JPXd2PXiXYsmFqEZd+cjh3/fx6e9NGCWKvfjXmTRuPxWytRU9eMJ1bvu+jra+qaUJGbasidmDhDj7JAWtrqlZG/N7rgzz56gDt6FVo67Fh882W4YUI+Li0Y1a/dQLh/N749qwLH2jrx3MbDKM1OwaJrywEAZ7t68OnB0/jOdRUx0/xOSwzoMSBStdDRYOTvjVz81Vj3OHvx/S/7bwIW7t+Nx2+rxIkzXfj5W3UozkzGjZUF2LDfAscwt5rTAwZ0IgpJrF4HMpsEv//qVNz3h8146C/bkJEcj5ZzdpjEtf3e9DHGu47DHDoRhSSWr5WkJMThK9NL0OPsRYu7N32vAn76xh5D7onLgE5EIRnYL784MxlP3DU5ZlJtf/jo0EXls0bdEzeklIuI3ATgdwDMAJ5TSi3VZFREpCuxfK0k2v1VImnYM3QRMQN4BsDNACoBfFVEKrUaGBGRFvzl8qOd4w+HUFIuVwFoUEodUkp1A3gJwB3aDIuISBuxnOPXWigpl2IAx71unwBwdWjDISLS1khaDxH2skUReRDAgwBQVqZtq0oiokDEco5fS6GkXBoBeG8qWOI+1o9SaplSqkopVZWXp81GrEREdLFQAvrnAMaLSIWIJAC4H8Cb2gyLiIiCNeyUi1LKISJ/B6AGrrLFF5RSdZqNjIiIghJSDl0ptRrAao3GQkREIeBKUSIig2BAJyIyCAZ0IiKDYEAnIjKIiG4SLSItAI5q8FS5AFo1eB6j4Pnoj+fjAp6L/vR6PsYopYZcyBPRgK4VEakNZAfskYLnoz+ejwt4Lvoz+vlgyoWIyCAY0ImIDEKvAX1ZtAcQY3g++uP5uIDnoj9Dnw9d5tCJiOhiep2hExHRADEf0EXkBRGxiMger2PZIrJWROrdH7OiOcZIEZFSEdkgIntFpE5EfuA+PlLPR5KIbBGRne7z8XP38QoR+UxEGkTkZXc30BFDRMwisl1E3nbfHrHnQ0SOiMhuEdkhIrXuY4Z9v8R8QAfwIoCbBhxbDGCdUmo8gHXu2yOBA8CPlFKVAGYC+Fv3Pq4j9XzYAcxWSk0BMBXATSIyE8CTAH6jlBoH4AyA70RxjNHwAwD7vG6P9PNxg1Jqqle5omHfLzEf0JVSHwFoG3D4DgDL3Z8vB7AwooOKEqXUKaXUNvfnHXC9aYsxcs+HUkqdc9+Md/9TAGYDeM19fMScDwAQkRIAtwJ4zn1bMILPhx+Gfb/EfED3o0Apdcr9eROAgmgOJhpEpBzANACfYQSfD3d6YQcAC4C1AA4CaFdKOdx3OQHXf3ojxW8BPAag1307ByP7fCgAa0Rkq3s7TMDA75ew7ykabkopJSIjqlRHREYBeB3AI0opq2sS5jLSzodSyglgqohkAngDwGVRHlLUiMhtACxKqa0icn20xxMjZimlGkUkH8BaEdnv/UWjvV/0OkNvFpFCAHB/tER5PBEjIvFwBfO/KKVWuA+P2PPhoZRqB7ABwDUAMkXEM1nxudetQVUDWCAiRwC8BFeq5XcYuecDSqlG90cLXP/hXwUDv1/0GtDfBLDI/fkiAKuiOJaIcedDnwewTyn1tNeXRur5yHPPzCEiyQDmwnVdYQOAe9x3GzHnQym1RClVopQqh2uP3/VKqa9jhJ4PEUkVkTTP5wDmAdgDA79fYn5hkYj8L4Dr4eqS1gzgZwBWAngFQBlc3RvvVUoNvHBqOCIyC8DHAHbjQo70H+DKo4/E83EFXBe1zHBNTl5RSv1CRC6Ba4aaDWA7gG8opezRG2nkuVMuP1ZK3TZSz4f7+37DfTMOwP8opX4lIjkw6Psl5gM6EREFRq8pFyIiGoABnYjIIBjQiYgMggGdiMggGNCJiAyCAZ2IyCAY0ImIDIIBnYjIIP4POLy1oZWNofwAAAAASUVORK5CYII=\n",
+ "text/plain": [
+ ""
+ ]
+ },
+ "metadata": {
+ "needs_background": "light"
+ },
+ "output_type": "display_data"
+ }
+ ],
+ "source": [
+ "x_arr = [j for j in dict(final).keys()]\n",
+ "y_arr = [dict(final)[j] for j in dict(final).keys()]\n",
+ "\n",
+ "x_arr_final = []\n",
+ "y_arr_final = []\n",
+ "\n",
+ "while (len(x_arr) > 0):\n",
+ "\n",
+ " x_arr_final.append(min(x_arr))\n",
+ " y_arr_final.append(y_arr[x_arr.index(min(x_arr))])\n",
+ " holder = x_arr.index(min(x_arr))\n",
+ " del x_arr[holder]\n",
+ " del y_arr[holder]\n",
+ "\n",
+ "plt.plot(x_arr_final, y_arr_final)\n",
+ "plt.scatter(x_arr_final, y_arr_final)\n",
+ "plt.show()"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "As you can see, we get a pretty strange probability distribution! This is due to the fact that repeated \n",
+ "applications of the Hadamard gate to the coin qubit (which you may recall was initialized in the $|\\downarrow\\rangle$ state). Over time, interference causes our coin qubit to bias to the left, but also creates a small bump far to \n",
+ "the right as well! If you think this is weird, do the math! Take a qubit in the initial state of $|1\\rangle$ \n",
+ "and repeatedlly apply a Hadamard transformation, then calculate the probabilities of measuring $|0\\rangle$ \n",
+ "and $|1\\rangle$ by taking the modulus squared of the probability amplitude corresponding to each of the states. \n",
+ "In fact, let's see what happens when our qubit is initialized in the $|\\uparrow\\rangle$ state: "
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 10,
+ "metadata": {},
+ "outputs": [
+ {
+ "name": "stdout",
+ "output_type": "stream",
+ "text": [
+ "Counter({52: 46, 50: 21, 44: 15, 12: 14, 54: 12, 42: 8, 48: 7, 16: 6, 10: 6, 40: 6, 32: 6, 30: 6, 26: 6, 46: 6, 38: 5, 34: 5, 36: 5, 22: 5, 28: 4, 14: 3, 24: 3, 56: 2, 18: 2, 20: 1})\n"
+ ]
+ },
+ {
+ "data": {
+ "image/png": "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\n",
+ "text/plain": [
+ ""
+ ]
+ },
+ "metadata": {
+ "needs_background": "light"
+ },
+ "output_type": "display_data"
+ }
+ ],
+ "source": [
+ "def initial_state():\n",
+ "\n",
+ " yield cirq.X.on(cirq.GridQubit(0, 1))\n",
+ "\n",
+ "number_qubits = 7\n",
+ "iterator = 30\n",
+ "sample_number = 200\n",
+ "\n",
+ "circuit = cirq.Circuit()\n",
+ "\n",
+ "circuit.append(initial_state())\n",
+ "\n",
+ "for j in range(0, iterator):\n",
+ " circuit.append(walk_step())\n",
+ "circuit.append(cirq.measure(*qubits, key='x'))\n",
+ "\n",
+ "simulator = cirq.Simulator()\n",
+ "result = simulator.run(circuit, repetitions=sample_number)\n",
+ "final = result.histogram(key='x')\n",
+ "\n",
+ "print(final)\n",
+ "\n",
+ "x_arr = [j for j in dict(final).keys()]\n",
+ "y_arr = [dict(final)[j] for j in dict(final).keys()]\n",
+ "\n",
+ "x_arr_final = []\n",
+ "y_arr_final = []\n",
+ "\n",
+ "while (len(x_arr) > 0):\n",
+ "\n",
+ " x_arr_final.append(min(x_arr))\n",
+ " y_arr_final.append(y_arr[x_arr.index(min(x_arr))])\n",
+ " holder = x_arr.index(min(x_arr))\n",
+ " del x_arr[holder]\n",
+ " del y_arr[holder]\n",
+ "\n",
+ "plt.plot(x_arr_final, y_arr_final)\n",
+ "plt.scatter(x_arr_final, y_arr_final)\n",
+ "plt.show()"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "Cool, right!? It's the mirror image of what we saw when the coin qubit was in the other state. Let's try one \n",
+ "more thing, let's initialize our coin qubit in a \"balanced\" state, where interference doesn't bias our \n",
+ "distribution towards only one side! We will set our initial state to:\n",
+ "\n",
+ "\n",
+ "$$|i\\rangle \\ = \\ \\frac{|\\uparrow\\rangle \\ + \\ i|\\downarrow\\rangle}{\\sqrt{2}}$$\n",
+ "\n",
+ "\n",
+ "This is easily implemented by applying a Hadamard gate to $|\\uparrow\\rangle$, and then applying an $S$ gate to \n",
+ "the qubit. When we simulate this with Cirq, we get:"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 11,
+ "metadata": {},
+ "outputs": [
+ {
+ "name": "stdout",
+ "output_type": "stream",
+ "text": [
+ "Counter({52: 31, 12: 26, 20: 13, 10: 12, 54: 10, 14: 10, 46: 9, 48: 9, 30: 8, 16: 8, 42: 8, 50: 7, 22: 6, 34: 6, 38: 6, 28: 5, 40: 4, 44: 4, 32: 4, 36: 4, 26: 3, 24: 3, 18: 2, 56: 1, 8: 1})\n"
+ ]
+ },
+ {
+ "data": {
+ "image/png": "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\n",
+ "text/plain": [
+ ""
+ ]
+ },
+ "metadata": {
+ "needs_background": "light"
+ },
+ "output_type": "display_data"
+ }
+ ],
+ "source": [
+ "def initial_state():\n",
+ "\n",
+ " yield cirq.X.on(cirq.GridQubit(0, 1))\n",
+ " \n",
+ " yield cirq.H.on(cirq.GridQubit(0, number_qubits))\n",
+ " yield cirq.S.on(cirq.GridQubit(0, number_qubits))\n",
+ "\n",
+ "number_qubits = 7\n",
+ "iterator = 30\n",
+ "sample_number = 200\n",
+ "\n",
+ "circuit = cirq.Circuit()\n",
+ "\n",
+ "circuit.append(initial_state())\n",
+ "\n",
+ "for j in range(0, iterator):\n",
+ " circuit.append(walk_step())\n",
+ "circuit.append(cirq.measure(*qubits, key='x'))\n",
+ "\n",
+ "simulator = cirq.Simulator()\n",
+ "result = simulator.run(circuit, repetitions=sample_number)\n",
+ "final = result.histogram(key='x')\n",
+ "\n",
+ "print(final)\n",
+ "\n",
+ "x_arr = [j for j in dict(final).keys()]\n",
+ "y_arr = [dict(final)[j] for j in dict(final).keys()]\n",
+ "\n",
+ "x_arr_final = []\n",
+ "y_arr_final = []\n",
+ "\n",
+ "while (len(x_arr) > 0):\n",
+ "\n",
+ " x_arr_final.append(min(x_arr))\n",
+ " y_arr_final.append(y_arr[x_arr.index(min(x_arr))])\n",
+ " holder = x_arr.index(min(x_arr))\n",
+ " del x_arr[holder]\n",
+ " del y_arr[holder]\n",
+ "\n",
+ "plt.plot(x_arr_final, y_arr_final)\n",
+ "plt.scatter(x_arr_final, y_arr_final)\n",
+ "plt.show()"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "So we get a probability distribution that is much more symetric!\n",
+ "\n",
+ "\n",
+ "Random walks have applications in so many fields of scientfific inquiry, ranging from biology, to \n",
+ "computer science, to finance. I definitely think there are a lot of possible great extensions to this basic \n",
+ "example of a QRW and many more great projects that can be made by utilizing this interesting process! \n",
+ "\n",
+ "**References**\n",
+ "\n",
+ "The first section of this tutorial was taken from this blog post (written by the same person who wrote this tutorial): https://lucaman99.github.io/blog/2019/08/03/Quantum-Random-Walks.html\n",
+ "\n",
+ "For more information about quantum random walks, see: https://arxiv.org/abs/quant-ph/0303081\n",
+ "\n",
+ "For more information about applications of random walks, see: https://en.wikipedia.org/wiki/Random_walk#Applications\n",
+ "\n"
+ ]
+ }
+ ],
+ "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.6.8"
+ }
+ },
+ "nbformat": 4,
+ "nbformat_minor": 2
+}