{ "cells": [ { "cell_type": "markdown", "metadata": {}, "source": [ "![(book cover)](https://covers.oreillystatic.com/images/0636920167433/cat.gif \"(book cover)\")\n", "# \"Programming Quantum Computers\" by O'Reilly Media - [book info](http://shop.oreilly.com/product/0636920167433.do) - [all code samples](https://oreilly-qc.github.io)\n", "\n", "## Code samples for Chapter 2\n", "These code samples were written by Andres Paz and Mariia Mykhailova." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### Example 2-1: Random bit" ] }, { "cell_type": "code", "execution_count": 1, "metadata": {}, "outputs": [ { "data": { "application/json": "[\"RandomBit\"]", "text/html": [ "" ], "text/plain": [ "RandomBit" ] }, "execution_count": 1, "metadata": {}, "output_type": "execute_result" } ], "source": [ "// Example 2-1: Random bit\n", "\n", "operation RandomBit () : Unit {\n", " // allocate one qubit\n", " use q = Qubit();\n", " // put it into superposition of 0 and 1\n", " H(q);\n", "\n", " // measure the qubit and store the result\n", " let bit = M(q);\n", "\n", " // make sure the qubit is back to the 0 state\n", " Reset(q);\n", "\n", " Message($\"{bit}\");\n", "}" ] }, { "cell_type": "code", "execution_count": 2, "metadata": { "scrolled": true }, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "Zero\r\n" ] }, { "data": { "application/json": "{\"@type\":\"tuple\"}", "text/plain": [ "()" ] }, "execution_count": 2, "metadata": {}, "output_type": "execute_result" } ], "source": [ "%simulate RandomBit" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### Example 2-2: Random byte" ] }, { "cell_type": "code", "execution_count": 3, "metadata": {}, "outputs": [ { "data": { "application/json": "[\"RandomByte\"]", "text/html": [ "" ], "text/plain": [ "RandomByte" ] }, "execution_count": 3, "metadata": {}, "output_type": "execute_result" } ], "source": [ "// Example 2-2: Random byte\n", "\n", "// open namespace which defines arithmetic operations\n", "open Microsoft.Quantum.Arithmetic;\n", "\n", "operation RandomByte () : Unit {\n", " // allocate 8 qubits\n", " use qs = Qubit[8];\n", " // put each qubit into superposition of 0 and 1\n", " ApplyToEach(H, qs);\n", "\n", " // measure the register and store the result\n", " // MeasureInteger returns the qubits to the |0⟩ state, so no separate Reset is required\n", " let randomByte = MeasureInteger(LittleEndian(qs));\n", "\n", " Message($\"{randomByte}\");\n", "}" ] }, { "cell_type": "code", "execution_count": 4, "metadata": { "scrolled": true }, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "224\r\n" ] }, { "data": { "application/json": "{\"@type\":\"tuple\"}", "text/plain": [ "()" ] }, "execution_count": 4, "metadata": {}, "output_type": "execute_result" } ], "source": [ "%simulate RandomByte" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### Example 2-3: Root-of-NOT" ] }, { "cell_type": "code", "execution_count": 5, "metadata": {}, "outputs": [ { "data": { "application/json": "[\"SqrtNOT\",\"RunSqrtNOT\"]", "text/html": [ "" ], "text/plain": [ "SqrtNOT, RunSqrtNOT" ] }, "execution_count": 5, "metadata": {}, "output_type": "execute_result" } ], "source": [ "// Example 2-3: Root-of-NOT\n", "\n", "open Microsoft.Quantum.Diagnostics;\n", "\n", "operation SqrtNOT (q : Qubit) : Unit is Adj+Ctl {\n", " H(q);\n", " S(q);\n", " H(q);\n", "}\n", "\n", "operation RunSqrtNOT () : Unit {\n", " // print matrix of the SqrtNOT operation\n", " DumpOperation(1, ApplyToFirstQubitCA(SqrtNOT, _));\n", "\n", " // allocate a qubit\n", " use q = Qubit();\n", " // apply SqrtNOT gate to the |0⟩ state\n", " SqrtNOT(q);\n", " Message(\"Qubit state after the first application of SqrtNOT\");\n", " DumpMachine();\n", "\n", " // apply SqrtNOT gate again and verify that the qubit ends up in the |1⟩ state\n", " SqrtNOT(q);\n", " Message(\"Qubit state after the second application of SqrtNOT\");\n", " DumpMachine();\n", "\n", " // make sure the qubit is back to the 0 state\n", " Reset(q);\n", "}" ] }, { "cell_type": "code", "execution_count": 6, "metadata": { "scrolled": true }, "outputs": [ { "data": { "text/html": [ "\r\n", " \r\n", " \r\n", " \r\n", " \r\n", "\r\n", " \r\n", " \r\n", " \r\n", " \r\n", "
Qubit IDs1\r\n", "
Unitary representation$$\r\n", " \\left(\\begin{matrix}\r\n", " 0.5 + 0.5i & 0.5 - 0.5i \\\\\n", "0.5 - 0.5i & 0.5 + 0.5i\r\n", " \\end{matrix}\\right)\r\n", " $$
\r\n", " " ], "text/plain": [ "Real:\n", "[[0.5000000000000001, 0.5000000000000001], \r\n", "[0.5000000000000001, 0.5000000000000001]]\n", "Imag:\n", "[[0.5000000000000001, -0.5000000000000001], \r\n", "[-0.5000000000000001, 0.5000000000000001]]" ] }, "metadata": {}, "output_type": "display_data" }, { "name": "stdout", "output_type": "stream", "text": [ "Qubit state after the first application of SqrtNOT\r\n" ] }, { "data": { "application/json": "{\"div_id\":\"dump-machine-div-d235bae9-4951-40d6-a3c9-847ce36cc3bb\",\"qubit_ids\":[1],\"n_qubits\":1,\"amplitudes\":[{\"Real\":0.5000000000000004,\"Imaginary\":0.5000000000000004,\"Magnitude\":0.7071067811865482,\"Phase\":0.7853981633974483},{\"Real\":0.5000000000000004,\"Imaginary\":-0.5000000000000004,\"Magnitude\":0.7071067811865482,\"Phase\":-0.7853981633974483}]}", "text/html": [ "\r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \n", "\r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", "
Qubit IDs1
Basis state (little endian)AmplitudeMeas. Pr.Phase
$\\left|0\\right\\rangle$$0.5000 + 0.5000 i$\r\n", " \r\n", " \r\n", "

\r\n", "

\r\n", "
\r\n", " ↑\r\n", "
$\\left|1\\right\\rangle$$0.5000 -0.5000 i$\r\n", " \r\n", " \r\n", "

\r\n", "

\r\n", "
\r\n", " ↑\r\n", "
" ], "text/plain": [ "|0⟩\t0.5000000000000004 + 0.5000000000000004𝑖\n", "|1⟩\t0.5000000000000004 + -0.5000000000000004𝑖" ] }, "metadata": {}, "output_type": "display_data" }, { "name": "stdout", "output_type": "stream", "text": [ "Qubit state after the second application of SqrtNOT\r\n" ] }, { "data": { "application/json": "{\"div_id\":\"dump-machine-div-8b368ea2-7553-4991-ad98-595d76347db1\",\"qubit_ids\":[1],\"n_qubits\":1,\"amplitudes\":[{\"Real\":4.930380657631324E-32,\"Imaginary\":-4.930380657631324E-32,\"Magnitude\":6.972611193684198E-32,\"Phase\":-0.7853981633974483},{\"Real\":1.000000000000001,\"Imaginary\":-4.930380657631324E-32,\"Magnitude\":1.000000000000001,\"Phase\":-4.9303806576313183E-32}]}", "text/html": [ "\r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \n", "\r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", " \r\n", "
Qubit IDs1
Basis state (little endian)AmplitudeMeas. Pr.Phase
$\\left|0\\right\\rangle$$0.0000 -0.0000 i$\r\n", " \r\n", " \r\n", "

\r\n", "

\r\n", "
\r\n", " ↑\r\n", "
$\\left|1\\right\\rangle$$1.0000 -0.0000 i$\r\n", " \r\n", " \r\n", "

\r\n", "

\r\n", "
\r\n", " ↑\r\n", "
" ], "text/plain": [ "|0⟩\t4.930380657631324E-32 + -4.930380657631324E-32𝑖\n", "|1⟩\t1.000000000000001 + -4.930380657631324E-32𝑖" ] }, "metadata": {}, "output_type": "display_data" }, { "data": { "application/json": "{\"@type\":\"tuple\"}", "text/plain": [ "()" ] }, "execution_count": 6, "metadata": {}, "output_type": "execute_result" } ], "source": [ "%simulate RunSqrtNOT" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### Example 2-4: Quantum Spy Hunter" ] }, { "cell_type": "code", "execution_count": 7, "metadata": { "scrolled": true }, "outputs": [ { "data": { "application/json": "[\"GetRangomBit\",\"TryCatchASpy\",\"RunSpyHuntingProtocol\"]", "text/html": [ "" ], "text/plain": [ "GetRangomBit, TryCatchASpy, RunSpyHuntingProtocol" ] }, "execution_count": 7, "metadata": {}, "output_type": "execute_result" } ], "source": [ "// Example 2-4: Quantum Spy Hunter\n", "\n", "open Microsoft.Quantum.Diagnostics;\n", "open Microsoft.Quantum.Measurement;\n", "\n", "operation GetRangomBit () : Bool {\n", " use q = Qubit();\n", " H(q);\n", " return MResetZ(q) == One;\n", "}\n", "\n", "// operation that performs the spy hunting protocol, including spy simulation if necessary\n", "operation TryCatchASpy (spyPresent : Bool, spyAppliesH : Bool) : Bool {\n", " use (a, fiber, b) = (Qubit(), Qubit(), Qubit());\n", " // generate two random bits\n", " let (sendApplyH, sendValue) = (GetRangomBit(), GetRangomBit());\n", "\n", " // prepare Alice's qubit\n", " if (sendValue) {\n", " X(a);\n", " }\n", " if (sendApplyH) {\n", " H(a);\n", " }\n", "\n", " // send the qubit!\n", " SWAP(fiber, a);\n", "\n", " // activate the spy\n", " if (spyPresent) {\n", " if (spyAppliesH) {\n", " H(fiber);\n", " }\n", " let stolenData = M(fiber);\n", " if (spyAppliesH) {\n", " H(fiber);\n", " }\n", " }\n", "\n", " // receive the qubit!\n", " let receiveApplyH = GetRangomBit();\n", " SWAP(fiber, b);\n", " if (receiveApplyH) {\n", " H(b);\n", " }\n", " let receiveValue = (M(b) == One);\n", "\n", " // make sure all qubits are back to the 0 state\n", " ResetAll([a, fiber, b]);\n", "\n", " // Alice emails Bob to tell him her choice of operations and value.\n", " // If the choice matches and the value does not, there's a spy!\n", " return (sendApplyH == receiveApplyH) and (sendValue != receiveValue);\n", "}\n", "\n", "operation RunSpyHuntingProtocol () : Unit {\n", " let spyPresent = true;\n", " let spyAppliesH = false;\n", " Message($\"Settings: spy {spyPresent ? \"\" | \"not \"}present\" + \n", " (spyPresent ? $\", spy {spyAppliesH ? \"applies H\" | \"does not apply H\"}\" | \"\"));\n", " let nAttempts = 1000;\n", " mutable nCaught = 0;\n", " for i in 1 .. nAttempts {\n", " if (TryCatchASpy(spyPresent, spyAppliesH)) {\n", " set nCaught += 1;\n", " }\n", " }\n", " Message($\"Caught the spy in {nCaught} out of {nAttempts} attempts\");\n", "}" ] }, { "cell_type": "code", "execution_count": 8, "metadata": { "scrolled": false }, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "Settings: spy present, spy does not apply H\n", "Caught the spy in 129 out of 1000 attempts\n" ] }, { "data": { "application/json": "{\"@type\":\"tuple\"}", "text/plain": [ "()" ] }, "execution_count": 8, "metadata": {}, "output_type": "execute_result" } ], "source": [ "%simulate RunSpyHuntingProtocol" ] } ], "metadata": { "kernelspec": { "display_name": "Q#", "language": "qsharp", "name": "iqsharp" }, "language_info": { "file_extension": ".qs", "mimetype": "text/x-qsharp", "name": "qsharp", "version": "0.14" } }, "nbformat": 4, "nbformat_minor": 2 }