Skip to content

Commit

Permalink
Unitary Synthesis of ChoiMixTableau for Diagonalisation (#941)
Browse files Browse the repository at this point in the history
* Copy files over from refactor/pauligraph

* Make identity pauli gadget still have correct qubits

* Remove unused line

* Rewrite ChoiMixTableauConverter to make easier to follow

* Combine diagonalisation steps

* Remove separate methods for solving post, init, and collapse spaces

* Split method into sections again for readability

* Rewrite header description

* Bump tket version

* Remove unused function

* Add tests for coverage

* Fix failing coverage tests

* Make gadget synthesis only use CXs to comply with test analysis

* Synthesising gadget pairs with a consistent CXConfigType varies performance figures

* Apply suggestions from code review

Co-authored-by: Alec Edgington <[email protected]>

* Update tket/src/Converters/ChoiMixTableauConverters.cpp

Co-authored-by: Alec Edgington <[email protected]>

* Implement most reviewer feedback

* Bump tket version number

* Doxygen error and formatting

* Initial implementation attempt

* Solve a bunch of linker errors

* Test comparators

* Test multiplications

* Tested hashing

* Refactor Utils, OpType, Ops, Gate, Clifford

* Refactored source and tests; some tests fail

* Fix test errors

* Binders compile, failing json validation

* Attempt to make serialisation backwards compatible

* Fix remaining serialisation bugs

* Fixed it!

* Rename PauliStrings2 to PauliTensor

* Remove old PauliStrings

* Rename test_PauliString2

* Rename file references

* File references in CMakeLists

* Bump tket version number

* Run formatter

* Fix binder errors

* Compiler errors on other OSs on CI

* More merge conflicts from deleted files

* Fix stub changes

* Test coverage

* Fix comparison issue

* Remove commented out code

* Implement reviewer feedback

* Bump tket version numbers

* Docs formatting error on CI

* Retain fix from merge conflict

* Fix merge bugs

* Error in merge

* Bump tket version number

* Missing TKET_ASSERTs from reviewer suggestions

* Test Z,X,H methods on UnitaryTableau for coverage

* Mixed initialisation test didn't actually use them

* Remove unused function

---------

Co-authored-by: Alec Edgington <[email protected]>
  • Loading branch information
willsimmons1465 and cqc-alec authored Nov 7, 2023
1 parent 02b7a62 commit ff68b3e
Show file tree
Hide file tree
Showing 29 changed files with 2,464 additions and 1,555 deletions.
2 changes: 1 addition & 1 deletion pytket/conanfile.py
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ def package(self):
cmake.install()

def requirements(self):
self.requires("tket/1.2.64@tket/stable")
self.requires("tket/1.2.65@tket/stable")
self.requires("tklog/0.3.3@tket/stable")
self.requires("tkrng/0.3.3@tket/stable")
self.requires("tkassert/0.3.3@tket/stable")
Expand Down
6 changes: 3 additions & 3 deletions pytket/tests/ansatz_sequence_test.py
Original file line number Diff line number Diff line change
Expand Up @@ -88,9 +88,9 @@ def test_nontrivial_sequence() -> None:
GraphColourMethod.Exhaustive: (3, 28, 20, 19),
},
PauliPartitionStrat.NonConflictingSets: {
GraphColourMethod.LargestFirst: (6, 28, 28, 28),
GraphColourMethod.Lazy: (6, 28, 28, 26),
GraphColourMethod.Exhaustive: (6, 28, 28, 26),
GraphColourMethod.LargestFirst: (6, 28, 28, 26),
GraphColourMethod.Lazy: (6, 28, 28, 28),
GraphColourMethod.Exhaustive: (6, 28, 28, 28),
},
}

Expand Down
2 changes: 0 additions & 2 deletions tket/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -222,7 +222,6 @@ target_sources(tket
src/ZX/MBQCRewrites.cpp
src/ZX/ZXRWSequences.cpp
src/Converters/ChoiMixTableauConverters.cpp
src/Converters/PauliGadget.cpp
src/Converters/PauliGraphConverters.cpp
src/Converters/Gauss.cpp
src/Converters/PhasePoly.cpp
Expand Down Expand Up @@ -373,7 +372,6 @@ target_sources(tket
include/tket/ZX/ZXGenerator.hpp
include/tket/Converters/Converters.hpp
include/tket/Converters/Gauss.hpp
include/tket/Converters/PauliGadget.hpp
include/tket/Converters/PhasePoly.hpp
include/tket/Converters/UnitaryTableauBox.hpp
include/tket/Placement/NeighbourPlacements.hpp
Expand Down
2 changes: 1 addition & 1 deletion tket/conanfile.py
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@

class TketConan(ConanFile):
name = "tket"
version = "1.2.64"
version = "1.2.65"
package_type = "library"
license = "Apache 2"
homepage = "https://github.com/CQCL/tket"
Expand Down
26 changes: 21 additions & 5 deletions tket/include/tket/Circuit/CircUtils.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -111,13 +111,13 @@ std::pair<Circuit, Complex> decompose_2cx_DV(const Eigen::Matrix4cd& U);
* Construct a phase gadget
*
* @param n_qubits number of qubits
* @param t phase parameter
* @param angle phase parameter
* @param cx_config CX configuration
*
* @return phase gadget implementation wrapped in a ConjugationBox
*/
Circuit phase_gadget(
unsigned n_qubits, const Expr& t,
unsigned n_qubits, const Expr& angle,
CXConfigType cx_config = CXConfigType::Snake);

/**
Expand All @@ -127,13 +127,29 @@ Circuit phase_gadget(
* \f$ e^{-\frac12 i \pi t \sigma_0 \otimes \sigma_1 \otimes \cdots} \f$
* where \f$ \sigma_i \in \{I,X,Y,Z\} \f$ are the Pauli operators.
*
* @param paulis Pauli operators
* @param t angle in half-turns
* @param paulis Pauli operators; coefficient gives rotation angle in half-turns
* @param cx_config CX configuration
* @return Pauli gadget implementation wrapped in a ConjugationBox
*/
Circuit pauli_gadget(
const std::vector<Pauli>& paulis, const Expr& t,
SpSymPauliTensor paulis, CXConfigType cx_config = CXConfigType::Snake);

/**
* Construct a circuit realising a pair of Pauli gadgets with the fewest
* two-qubit gates.
*
* The returned circuit implements the unitary e^{-i pi angle1 paulis1 / 2}
* e^{-i pi angle0 paulis0 / 2}, i.e. a gadget of angle0 about paulis0 followed
* by a gadget of angle1 about paulis1.
*
* @param paulis0 Pauli operators for first gadget; coefficient gives rotation
* angle in half-turns
* @param paulis1 Pauli operators for second gadget; coefficient gives rotation
* angle in half-turns
* @param cx_config CX configuration
*/
Circuit pauli_gadget_pair(
SpSymPauliTensor paulis0, SpSymPauliTensor paulis1,
CXConfigType cx_config = CXConfigType::Snake);

/**
Expand Down
42 changes: 42 additions & 0 deletions tket/include/tket/Circuit/PauliExpBoxes.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -202,4 +202,46 @@ class PauliExpCommutingSetBox : public Box {
CXConfigType cx_config_;
};

/**
* Constructs a PauliExpBox for a single pauli gadget and appends it to a
* circuit.
*
* @param circ The circuit to append the box to
* @param pauli The pauli operator of the gadget; coefficient gives the rotation
* angle in half-turns
* @param cx_config The CX configuration to be used during synthesis
*/
void append_single_pauli_gadget_as_pauli_exp_box(
Circuit &circ, const SpSymPauliTensor &pauli, CXConfigType cx_config);

/**
* Constructs a PauliExpPairBox for a pair of pauli gadgets and appends it to a
* circuit. The pauli gadgets may or may not commute, so the ordering matters.
*
* @param circ The circuit to append the box to
* @param pauli0 The pauli operator of the first gadget; coefficient gives the
* rotation angle in half-turns
* @param pauli1 The pauli operator of the second gadget; coefficient gives the
* rotation angle in half-turns
* @param cx_config The CX configuration to be used during synthesis
*/
void append_pauli_gadget_pair_as_box(
Circuit &circ, const SpSymPauliTensor &pauli0,
const SpSymPauliTensor &pauli1, CXConfigType cx_config);

/**
* Constructs a PauliExpCommutingSetBox for a set of mutually commuting pauli
* gadgets and appends it to a circuit. As the pauli gadgets all commute, the
* ordering does not matter semantically, but may yield different synthesised
* circuits.
*
* @param circ The circuit to append the box to
* @param gadgets Description of the pauli gadgets; coefficients give the
* rotation angles in half-turns
* @param cx_config The CX configuration to be used during synthesis
*/
void append_commuting_pauli_gadget_set_as_box(
Circuit &circ, const std::list<SpSymPauliTensor> &gadgets,
CXConfigType cx_config);

} // namespace tket
21 changes: 18 additions & 3 deletions tket/include/tket/Clifford/ChoiMixTableau.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,8 @@ class ChoiMixTableau {
* When mapped to a sparse readable representation, independent
* SpPauliStabiliser objects are used for each segment, so we no longer expect
* their individual phases to be +-1, instead only requiring this on their
* product.
* product. get_row() will automatically transpose the input segment term so
* it is presented as RxS s.t. SCR = C.
*
* Columns of the tableau are indexed by pair of Qubit id and a tag to
* distinguish input vs output. Rows are not maintained in any particular
Expand Down Expand Up @@ -93,6 +94,7 @@ class ChoiMixTableau {
* Construct a tableau directly from its rows.
* Each row is represented as a product of SpPauliStabilisers where the first
* is over the input qubits and the second is over the outputs.
* A row RxS is a pair s.t. SCR = C
*/
explicit ChoiMixTableau(const std::list<row_tensor_t>& rows);
/**
Expand Down Expand Up @@ -122,13 +124,23 @@ class ChoiMixTableau {
* Get the number of boundaries representing outputs from the process.
*/
unsigned get_n_outputs() const;
/**
* Get all qubit names present in the input segment.
*/
qubit_vector_t input_qubits() const;
/**
* Get all qubit names present in the output segment.
*/
qubit_vector_t output_qubits() const;

/**
* Read off a row as a Pauli string
* Read off a row as a Pauli string.
* Returns a pair of Pauli strings RxS such that SCR = C
*/
row_tensor_t get_row(unsigned i) const;
/**
* Combine rows into a single row
* Combine rows into a single row.
* Returns a pair of Pauli strings RxS such that SCR = C
*/
row_tensor_t get_row_product(const std::vector<unsigned>& rows) const;

Expand All @@ -142,7 +154,10 @@ class ChoiMixTableau {
* outputs.
*/
void apply_S(const Qubit& qb, TableauSegment seg = TableauSegment::Output);
void apply_Z(const Qubit& qb, TableauSegment seg = TableauSegment::Output);
void apply_V(const Qubit& qb, TableauSegment seg = TableauSegment::Output);
void apply_X(const Qubit& qb, TableauSegment seg = TableauSegment::Output);
void apply_H(const Qubit& qb, TableauSegment seg = TableauSegment::Output);
void apply_CX(
const Qubit& control, const Qubit& target,
TableauSegment seg = TableauSegment::Output);
Expand Down
41 changes: 8 additions & 33 deletions tket/include/tket/Clifford/SymplecticTableau.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -20,12 +20,6 @@

namespace tket {

// Forward declare friend classes for converters
class ChoiMixTableau;
class UnitaryTableau;
class UnitaryRevTableau;
class Circuit;

/**
* Boolean encoding of Pauli
* <x, z> = <false, false> ==> I
Expand Down Expand Up @@ -136,10 +130,13 @@ class SymplecticTableau {
void row_mult(unsigned ra, unsigned rw, Complex coeff = 1.);

/**
* Applies an S/V/CX gate to the given qubit(s)
* Applies a chosen gate to the given qubit(s)
*/
void apply_S(unsigned qb);
void apply_Z(unsigned qb);
void apply_V(unsigned qb);
void apply_X(unsigned qb);
void apply_H(unsigned qb);
void apply_CX(unsigned qc, unsigned qt);
void apply_gate(OpType type, const std::vector<unsigned> &qbs);

Expand Down Expand Up @@ -173,29 +170,19 @@ class SymplecticTableau {
*/
void gaussian_form();

private:
/**
* Number of rows
*/
unsigned n_rows_;

/**
* Number of qubits in each row
*/
unsigned n_qubits_;

/**
* Tableau contents
*/
MatrixXb xmat_;
MatrixXb zmat_;
VectorXb phase_;
MatrixXb xmat;
MatrixXb zmat;
VectorXb phase;

/**
* Complex conjugate of the state by conjugating rows
*/
SymplecticTableau conjugate() const;

private:
/**
* Helper methods for manipulating the tableau when applying gates
*/
Expand All @@ -206,18 +193,6 @@ class SymplecticTableau {
void col_mult(
const MatrixXb::ColXpr &a, const MatrixXb::ColXpr &b, bool flip,
MatrixXb::ColXpr &w, VectorXb &pw);

friend class UnitaryTableau;
friend class ChoiMixTableau;
friend Circuit unitary_tableau_to_circuit(const UnitaryTableau &tab);
friend std::pair<Circuit, unit_map_t> cm_tableau_to_circuit(
const ChoiMixTableau &tab);
friend std::ostream &operator<<(std::ostream &os, const UnitaryTableau &tab);
friend std::ostream &operator<<(
std::ostream &os, const UnitaryRevTableau &tab);

friend void to_json(nlohmann::json &j, const SymplecticTableau &tab);
friend void from_json(const nlohmann::json &j, SymplecticTableau &tab);
};

JSON_DECL(SymplecticTableau)
Expand Down
12 changes: 12 additions & 0 deletions tket/include/tket/Clifford/UnitaryTableau.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -101,8 +101,14 @@ class UnitaryTableau {
*/
void apply_S_at_front(const Qubit& qb);
void apply_S_at_end(const Qubit& qb);
void apply_Z_at_front(const Qubit& qb);
void apply_Z_at_end(const Qubit& qb);
void apply_V_at_front(const Qubit& qb);
void apply_V_at_end(const Qubit& qb);
void apply_X_at_front(const Qubit& qb);
void apply_X_at_end(const Qubit& qb);
void apply_H_at_front(const Qubit& qb);
void apply_H_at_end(const Qubit& qb);
void apply_CX_at_front(const Qubit& control, const Qubit& target);
void apply_CX_at_end(const Qubit& control, const Qubit& target);
void apply_gate_at_front(OpType type, const qubit_vector_t& qbs);
Expand Down Expand Up @@ -236,8 +242,14 @@ class UnitaryRevTableau {
*/
void apply_S_at_front(const Qubit& qb);
void apply_S_at_end(const Qubit& qb);
void apply_Z_at_front(const Qubit& qb);
void apply_Z_at_end(const Qubit& qb);
void apply_V_at_front(const Qubit& qb);
void apply_V_at_end(const Qubit& qb);
void apply_X_at_front(const Qubit& qb);
void apply_X_at_end(const Qubit& qb);
void apply_H_at_front(const Qubit& qb);
void apply_H_at_end(const Qubit& qb);
void apply_CX_at_front(const Qubit& control, const Qubit& target);
void apply_CX_at_end(const Qubit& control, const Qubit& target);
void apply_gate_at_front(OpType type, const qubit_vector_t& qbs);
Expand Down
Loading

0 comments on commit ff68b3e

Please sign in to comment.