Skip to content

Commit

Permalink
Launch Cirq-FT: Cirq for Fault Tolerant Algorithms sub-package (#6138)
Browse files Browse the repository at this point in the history
* Launch Cirq-FT: Cirq for Fault Tolerant Algorithms sub-package

* Use cirq._compat.cached_property instead of functools.cached_property

* Update requirements.txt to include notebook specific dependencies

* import Literal from typing_extensions

* More Python3.7 compatability fixes

* Yet backwards incompatibility fix

* More backwards incompatibility fixes

* Do not use unicode characters in phase_estimation_of_quantum_walk.ipynb to make windows happy.

* Fix failing doctests

* Add a LOT more tests and fix failing coverage check

* LOTS of docstring improvements to address Dougs comments
  • Loading branch information
tanujkhattar authored Jun 13, 2023
1 parent 26af12e commit c5dbb11
Show file tree
Hide file tree
Showing 83 changed files with 11,784 additions and 16 deletions.
2 changes: 1 addition & 1 deletion cirq-core/cirq/contrib/svg/svg_test.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
# pylint: disable=wrong-or-nonexistent-copyright-notice
import IPython.display # type: ignore[import]
import IPython.display
import numpy as np
import pytest

Expand Down
21 changes: 12 additions & 9 deletions cirq-ft/README.rst
Original file line number Diff line number Diff line change
Expand Up @@ -3,21 +3,24 @@
:alt: cirq-ft
:width: 500px

TODO(#6119,tanujkhattar): please review and update as needed
Cirq-FT: Cirq for Fault-Tolerant algorithms
-------------------------------------------

Cirq is a Python library for writing, manipulating, and optimizing quantum
circuits and running them against quantum computers and simulators.

This module is **cirq-ft**, which enhances support for fault-tolerant algorithms
and provides functions for quantum memory management.
Cirq-FT is a Python library for rapid prototyping and resource estimation of fault tolerant
algorithms that extends the quantum computing SDK **Cirq**.

Installation
------------
Cirq-FT is currently in beta mode and only available as a pre-release.
To install the pre-release version of **cirq-ft**, use

.. code-block:: bash
pip install cirq-ft --pre
To install the stable version of only **cirq-ft**, use `pip install cirq-ft`.
To install the pre-release version of only **cirq-ft**, use `pip install cirq-ft --pre`.
Note, that this will install both cirq-ft and cirq-core as well.

To get all the optional modules installed as well, you'll have to use `pip install cirq` or
To get all the optional **Cirq** modules installed as well, use `pip install cirq` or
`pip install cirq --pre` for the pre-release version.
42 changes: 42 additions & 0 deletions cirq-ft/cirq_ft/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -13,3 +13,45 @@
# limitations under the License.

from cirq_ft._version import __version__
from cirq_ft.algos import (
QROM,
AdditionGate,
AddMod,
And,
ApplyGateToLthQubit,
ContiguousRegisterGate,
GenericSelect,
LessThanEqualGate,
LessThanGate,
MultiControlPauli,
MultiTargetCNOT,
MultiTargetCSwap,
MultiTargetCSwapApprox,
PrepareHubbard,
PrepareOracle,
PrepareUniformSuperposition,
ProgrammableRotationGateArray,
ProgrammableRotationGateArrayBase,
QubitizationWalkOperator,
ReflectionUsingPrepare,
SelectedMajoranaFermionGate,
SelectHubbard,
SelectOracle,
SelectSwapQROM,
StatePreparationAliasSampling,
SwapWithZeroGate,
UnaryIterationGate,
unary_iteration,
)
from cirq_ft.infra import (
GateWithRegisters,
GreedyQubitManager,
Register,
Registers,
SelectionRegister,
SelectionRegisters,
TComplexity,
map_clean_and_borrowable_qubits,
t_complexity,
testing,
)
40 changes: 40 additions & 0 deletions cirq-ft/cirq_ft/algos/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
# Copyright 2023 The Cirq Developers
#
# 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
#
# https://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.

from cirq_ft.algos.and_gate import And
from cirq_ft.algos.apply_gate_to_lth_target import ApplyGateToLthQubit
from cirq_ft.algos.arithmetic_gates import (
AdditionGate,
AddMod,
ContiguousRegisterGate,
LessThanEqualGate,
LessThanGate,
)
from cirq_ft.algos.generic_select import GenericSelect
from cirq_ft.algos.hubbard_model import PrepareHubbard, SelectHubbard
from cirq_ft.algos.multi_control_multi_target_pauli import MultiControlPauli, MultiTargetCNOT
from cirq_ft.algos.prepare_uniform_superposition import PrepareUniformSuperposition
from cirq_ft.algos.programmable_rotation_gate_array import (
ProgrammableRotationGateArray,
ProgrammableRotationGateArrayBase,
)
from cirq_ft.algos.qrom import QROM
from cirq_ft.algos.qubitization_walk_operator import QubitizationWalkOperator
from cirq_ft.algos.reflection_using_prepare import ReflectionUsingPrepare
from cirq_ft.algos.select_and_prepare import PrepareOracle, SelectOracle
from cirq_ft.algos.select_swap_qrom import SelectSwapQROM
from cirq_ft.algos.selected_majorana_fermion import SelectedMajoranaFermionGate
from cirq_ft.algos.state_preparation import StatePreparationAliasSampling
from cirq_ft.algos.swap_network import MultiTargetCSwap, MultiTargetCSwapApprox, SwapWithZeroGate
from cirq_ft.algos.unary_iteration_gate import UnaryIterationGate, unary_iteration
225 changes: 225 additions & 0 deletions cirq-ft/cirq_ft/algos/and_gate.ipynb
Original file line number Diff line number Diff line change
@@ -0,0 +1,225 @@
{
"cells": [
{
"cell_type": "code",
"execution_count": null,
"id": "97385158",
"metadata": {},
"outputs": [],
"source": [
"# Copyright 2023 The Cirq Developers\n",
"#\n",
"# Licensed under the Apache License, Version 2.0 (the \"License\");\n",
"# you may not use this file except in compliance with the License.\n",
"# You may obtain a copy of the License at\n",
"#\n",
"# https://www.apache.org/licenses/LICENSE-2.0\n",
"#\n",
"# Unless required by applicable law or agreed to in writing, software\n",
"# distributed under the License is distributed on an \"AS IS\" BASIS,\n",
"# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n",
"# See the License for the specific language governing permissions and\n",
"# limitations under the License."
]
},
{
"cell_type": "markdown",
"id": "93353f4e",
"metadata": {},
"source": [
"# And\n",
"\n",
"To do classical logic with a reversible circuit (a pre-requisite for a quantum circuit), we use a three (qu)bit operation called a Toffoli gate that takes `[a, b, c]` to `[a, b, c ^ (a & b)]`. If we take `c` to be zero, this is an And gate taking `[a, b]` to `[a, b, a & b]`."
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "a95dab52",
"metadata": {},
"outputs": [],
"source": [
"import itertools\n",
"for a, b, in itertools.product([0, 1], repeat=2):\n",
" print(a, b, '->', a & b)"
]
},
{
"cell_type": "markdown",
"id": "37a44523",
"metadata": {},
"source": [
"## Quantum operation\n",
"\n",
"We provide a quantum operation for performing quantum And. Specifically, it assumes the third qubit (i.e. the target) is initialized to the `|0>` state."
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "5c456e50",
"metadata": {},
"outputs": [],
"source": [
"import cirq\n",
"from cirq.contrib.svg import SVGCircuit\n",
"from cirq_ft import And\n",
"\n",
"gate = And()\n",
"r = gate.registers\n",
"quregs = r.get_named_qubits()\n",
"operation = gate.on_registers(**quregs)\n",
"circuit = cirq.Circuit(operation)\n",
"SVGCircuit(circuit)"
]
},
{
"cell_type": "markdown",
"id": "8d4e16dc",
"metadata": {},
"source": [
"## Efficient decomposition\n",
"\n",
"This specialization of the Toffoli gate permits a specialized decomposition that minimizes the `T`-gate count."
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "fefe2934",
"metadata": {},
"outputs": [],
"source": [
"c2 = cirq.Circuit(cirq.decompose_once(operation))\n",
"SVGCircuit(c2)"
]
},
{
"cell_type": "markdown",
"id": "b91cc9d9",
"metadata": {},
"source": [
"## Test behavior\n",
"\n",
"We can test the behavior of the And gate on computational basis states using a Quantum simulator."
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "2ec57c0e",
"metadata": {},
"outputs": [],
"source": [
"input_states = [(a, b, 0) for a, b in itertools.product([0, 1], repeat=2)]\n",
"output_states = [(a, b, a & b) for a, b, _ in input_states]\n",
"\n",
"\n",
"for inp, out in zip(input_states, output_states):\n",
" result = cirq.Simulator().simulate(c2, initial_state=inp)\n",
" print(inp, '->', result.dirac_notation())\n",
" assert result.dirac_notation()[1:-1] == \"\".join(str(x) for x in out)"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "7e5832e4",
"metadata": {},
"outputs": [],
"source": [
"import numpy as np\n",
"inds, = np.where(abs(result.final_state_vector) > 1e-8)\n",
"assert len(inds) == 1\n",
"ind, = inds\n",
"f'{ind:3b}'"
]
},
{
"cell_type": "markdown",
"id": "fa451755",
"metadata": {},
"source": [
"## Uncompute\n",
"\n",
"We can save even more `T` gates when \"uncomputing\" an And operation, i.e. performing the adjoint operation by using classical control."
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "a2878f83",
"metadata": {},
"outputs": [],
"source": [
"inv_operation = operation ** -1\n",
"inv_circuit = cirq.Circuit(inv_operation)\n",
"SVGCircuit(inv_circuit)"
]
},
{
"cell_type": "markdown",
"id": "3a2dcf07",
"metadata": {},
"source": [
"We reset our target using measurement and fix up phases depending on the result of that measurement:"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "bd123481",
"metadata": {},
"outputs": [],
"source": [
"inv_c2 = cirq.Circuit(cirq.decompose_once(inv_operation))\n",
"inv_c2"
]
},
{
"cell_type": "markdown",
"id": "a99e3bf5",
"metadata": {},
"source": [
"## Test Adjoint"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "3cacf727",
"metadata": {},
"outputs": [],
"source": [
"input_states = [(a, b, a & b) for a, b in itertools.product([0, 1], repeat=2)]\n",
"output_states = [(a, b, 0) for a, b, _ in input_states]\n",
"\n",
"for inp, out in zip(input_states, output_states):\n",
" result = cirq.Simulator().simulate(inv_circuit, initial_state=inp)\n",
" print(inp, '->', result.dirac_notation())\n",
" assert result.dirac_notation()[1:-1] == \"\".join(str(x) for x in out)"
]
}
],
"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.8.16"
}
},
"nbformat": 4,
"nbformat_minor": 5
}
Loading

0 comments on commit c5dbb11

Please sign in to comment.