Repository: HQSquantumsimulations/qoqo (language: python)

Issue:
activating github actions



Discussion / hints:

Fix patch:
diff --git a/qoqo/examples/Intro_to_qoqo.ipynb b/qoqo/examples/Intro_to_qoqo.ipynb
index ce99ec03..31410766 100644
--- a/qoqo/examples/Intro_to_qoqo.ipynb
+++ b/qoqo/examples/Intro_to_qoqo.ipynb
@@ -2,8 +2,6 @@
  "cells": [
   {
    "cell_type": "markdown",
-   "id": "linear-albania",
-   "metadata": {},
    "source": [
     "# Introduction to Qoqo\n",
     "Quantum Operation Quantum Operation  \n",
@@ -19,45 +17,29 @@
     "* A decomposer translating circuits to a specific set of gates\n",
     "* A quantum circuit optimizer\n",
     "* A collection of quantum algorithms\n"
-   ]
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "markdown",
-   "id": "amber-jungle",
-   "metadata": {},
    "source": [
     "## A simple circuit and measurement\n",
     "\n",
     "We show the construction of a simple entangling circuit and an observable measurement based on this circuit"
-   ]
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "markdown",
-   "id": "secondary-accused",
-   "metadata": {},
    "source": [
     "### Entangling circuit snippet\n",
     "Similar to many other toolkits the unitary entangling circuit can be constructed by adding operations to a circuit"
-   ]
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "code",
-   "execution_count": 1,
-   "id": "capable-dallas",
-   "metadata": {},
-   "outputs": [
-    {
-     "name": "stdout",
-     "output_type": "stream",
-     "text": [
-      "Hadamard(Hadamard { qubit: 0 })\n",
-      "CNOT(CNOT { control: 0, target: 1 })\n",
-      "\n",
-      "2\n",
-      "{'Hadamard', 'CNOT'}\n"
-     ]
-    }
-   ],
+   "execution_count": 4,
    "source": [
     "from qoqo import Circuit\n",
     "from qoqo import operations as ops\n",
@@ -71,42 +53,35 @@
     "\n",
     "assert len(circuit_snippet) == 2\n",
     "assert circuit_snippet.get_operation_types() == set(['Hadamard', 'CNOT'])"
-   ]
+   ],
+   "outputs": [
+    {
+     "output_type": "stream",
+     "name": "stdout",
+     "text": [
+      "Hadamard(Hadamard { qubit: 0 })\n",
+      "CNOT(CNOT { control: 0, target: 1 })\n",
+      "\n",
+      "2\n",
+      "{'Hadamard', 'CNOT'}\n"
+     ]
+    }
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "markdown",
-   "id": "marine-socket",
-   "metadata": {},
    "source": [
     "### Measuring qubits\n",
     "Qoqo uses classical registers for the readout. We need to add a classical register definition to the circuit and a measurement statement.\n",
     "The number of projective measurements can be directly set in the circuit.  \n",
     "The simulation and measurement of the circuit is handled by the qoqo_pyquest interface (in this example)."
-   ]
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "code",
-   "execution_count": 2,
-   "id": "middle-emerald",
-   "metadata": {},
-   "outputs": [
-    {
-     "name": "stdout",
-     "output_type": "stream",
-     "text": [
-      "[1, 1]\n",
-      "[1, 1]\n",
-      "[1, 1]\n",
-      "[0, 0]\n",
-      "[0, 0]\n",
-      "[1, 1]\n",
-      "[1, 1]\n",
-      "[1, 1]\n",
-      "[1, 1]\n",
-      "[1, 1]\n"
-     ]
-    }
-   ],
+   "execution_count": 5,
    "source": [
     "from qoqo_pyquest import PyQuestBackend\n",
     "from qoqo import Circuit\n",
@@ -123,33 +98,39 @@
     "    print(single_projective_measurement)\n",
     "    \n",
     "assert len(result_bit_registers['ro']) == 10"
-   ]
+   ],
+   "outputs": [
+    {
+     "output_type": "stream",
+     "name": "stdout",
+     "text": [
+      "[1.0, 1.0]\n",
+      "[0.0, 0.0]\n",
+      "[1.0, 1.0]\n",
+      "[1.0, 1.0]\n",
+      "[0.0, 0.0]\n",
+      "[0.0, 0.0]\n",
+      "[0.0, 0.0]\n",
+      "[1.0, 1.0]\n",
+      "[1.0, 1.0]\n",
+      "[1.0, 1.0]\n"
+     ]
+    }
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "markdown",
-   "id": "interesting-screw",
-   "metadata": {},
    "source": [
     "### Measuring Observables\n",
     "Qoqo includes the direct evaluation of projective measurements to an observable measurement e.g. 3 * < Z0 > + < Z0 Z1 >  \n",
     "The measurement is defined by a set of expectation values of a product of pauli operators and a matrix that combines the expectation values  "
-   ]
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "code",
-   "execution_count": 3,
-   "id": "impossible-civilization",
-   "metadata": {},
-   "outputs": [
-    {
-     "name": "stdout",
-     "output_type": "stream",
-     "text": [
-      "{}\n",
-      "Result of DoUnitary -1.0\n"
-     ]
-    }
-   ],
+   "execution_count": 6,
    "source": [
     "from qoqo.measurements import BasisRotationInput, BasisRotation\n",
     "from qoqo import DoUnitary\n",
@@ -182,30 +163,34 @@
     "\n",
     "assert res > -4.0 * 10\n",
     "assert res < 4.0 * 10"
-   ]
+   ],
+   "outputs": [
+    {
+     "output_type": "error",
+     "ename": "TypeError",
+     "evalue": "'float' object cannot be interpreted as an integer",
+     "traceback": [
+      "\u001b[0;31m---------------------------------------------------------------------------\u001b[0m",
+      "\u001b[0;31mTypeError\u001b[0m                                 Traceback (most recent call last)",
+      "\u001b[0;32m/tmp/ipykernel_5360/2486775377.py\u001b[0m in \u001b[0;36m<module>\u001b[0;34m\u001b[0m\n\u001b[1;32m     24\u001b[0m \u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m     25\u001b[0m \u001b[0mdo_unitary\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0mDoUnitary\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mmeasurement\u001b[0m\u001b[0;34m=\u001b[0m\u001b[0mmeasurement\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mbackend\u001b[0m\u001b[0;34m=\u001b[0m\u001b[0mbackend\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mfree_parameters\u001b[0m\u001b[0;34m=\u001b[0m\u001b[0;34m[\u001b[0m\u001b[0;34m]\u001b[0m\u001b[0;34m)\u001b[0m \u001b[0;31m# This quantum program does not have any free parameters\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0;32m---> 26\u001b[0;31m \u001b[0mres\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0mdo_unitary\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m[\u001b[0m\u001b[0;34m\"example\"\u001b[0m\u001b[0;34m]\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m\u001b[1;32m     27\u001b[0m \u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m     28\u001b[0m \u001b[0mprint\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0;34m\"Result of DoUnitary\"\u001b[0m\u001b[0;34m,\u001b[0m \u001b[0mres\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n",
+      "\u001b[0;32m~/.local/lib/python3.8/site-packages/qoqo/do_unitary/do_unitary.py\u001b[0m in \u001b[0;36m__call__\u001b[0;34m(self, parameters)\u001b[0m\n\u001b[1;32m    107\u001b[0m         \u001b[0mrun_measurement\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0mself\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0m_measurement\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0msubstitute_parameters\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mparameter_substitution_dict\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m    108\u001b[0m \u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0;32m--> 109\u001b[0;31m         \u001b[0mexpectation_values\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0mself\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0m_backend\u001b[0m\u001b[0;34m.\u001b[0m\u001b[0mrun_measurement\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0mrun_measurement\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m\u001b[1;32m    110\u001b[0m         \u001b[0;32mif\u001b[0m \u001b[0mexpectation_values\u001b[0m \u001b[0;32mis\u001b[0m \u001b[0;32mNone\u001b[0m\u001b[0;34m:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m    111\u001b[0m             \u001b[0;31m# if self._resume_file_name is not None:\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n",
+      "\u001b[0;32m~/.local/lib/python3.8/site-packages/qoqo_pyquest/backend/pyquest_cffi_backend.py\u001b[0m in \u001b[0;36mrun_measurement\u001b[0;34m(self, measurement)\u001b[0m\n\u001b[1;32m    217\u001b[0m             \u001b[0moutput_float_register_dict\u001b[0m\u001b[0;34m,\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m    218\u001b[0m             output_complex_register_dict) = self.run_measurement_registers(measurement)\n\u001b[0;32m--> 219\u001b[0;31m         return measurement.evaluate(\n\u001b[0m\u001b[1;32m    220\u001b[0m             \u001b[0moutput_bit_register_dict\u001b[0m\u001b[0;34m,\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m    221\u001b[0m             \u001b[0moutput_float_register_dict\u001b[0m\u001b[0;34m,\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n",
+      "\u001b[0;31mTypeError\u001b[0m: 'float' object cannot be interpreted as an integer"
+     ]
+    }
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "markdown",
-   "id": "typical-contract",
-   "metadata": {},
    "source": [
     "### De/Serializing the quantum program"
-   ]
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "code",
-   "execution_count": 4,
-   "id": "generous-voluntary",
-   "metadata": {},
-   "outputs": [
-    {
-     "name": "stdout",
-     "output_type": "stream",
-     "text": [
-      "{\"constant_circuit\":null,\"circuits\":[{\"definitions\":[{\"DefinitionBit\":{\"name\":\"ro\",\"length\":2,\"is_output\":true}}],\"operations\":[{\"Hadamard\":{\"qubit\":0}},{\"CNOT\":{\"control\":0,\"target\":1}},{\"PragmaRepeatedMeasurement\":{\"readout\":\"ro\",\"qubit_mapping\":null,\"number_measurements\":10}}]}],\"input\":{\"pauli_product_qubit_masks\":{\"ro\":{\"1\":[0,1],\"0\":[0]}},\"number_qubits\":2,\"number_pauli_products\":2,\"measured_exp_vals\":{\"example\":{\"Linear\":{\"0\":3.0,\"1\":1.0}}},\"use_flipped_measurement\":false}}\n"
-     ]
-    }
-   ],
+   "execution_count": null,
    "source": [
     "from qoqo.measurements import BasisRotationInput, BasisRotation\n",
     "from qoqo import DoUnitary\n",
@@ -234,39 +219,31 @@
     "print(measurement_json)\n",
     "\n",
     "assert measurement_json != \"\""
-   ]
+   ],
+   "outputs": [
+    {
+     "output_type": "stream",
+     "name": "stdout",
+     "text": [
+      "{\"constant_circuit\":null,\"circuits\":[{\"definitions\":[{\"DefinitionBit\":{\"name\":\"ro\",\"length\":2,\"is_output\":true}}],\"operations\":[{\"Hadamard\":{\"qubit\":0}},{\"CNOT\":{\"control\":0,\"target\":1}},{\"PragmaRepeatedMeasurement\":{\"readout\":\"ro\",\"qubit_mapping\":null,\"number_measurements\":10}}]}],\"input\":{\"pauli_product_qubit_masks\":{\"ro\":{\"1\":[0,1],\"0\":[0]}},\"number_qubits\":2,\"number_pauli_products\":2,\"measured_exp_vals\":{\"example\":{\"Linear\":{\"0\":3.0,\"1\":1.0}}},\"use_flipped_measurement\":false}}\n"
+     ]
+    }
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "markdown",
-   "id": "parliamentary-statistics",
-   "metadata": {},
    "source": [
     "## Fine control over decoherence\n",
     "Qoqo allows full control over decoherence by placing decoherence operations in the circuit on the same level as gates.  \n",
     "Example: Letting only one qubit decay.  \n",
     "The backend automatically switches from statevector simulation to density matrix simulation in the presence of noise."
-   ]
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "code",
-   "execution_count": 5,
-   "id": "dedicated-plane",
-   "metadata": {},
-   "outputs": [
-    {
-     "name": "stdout",
-     "output_type": "stream",
-     "text": [
-      "DefinitionBit(DefinitionBit { name: \"ro\", length: 2, is_output: true })\n",
-      "PauliX(PauliX { qubit: 0 })\n",
-      "PauliX(PauliX { qubit: 1 })\n",
-      "PragmaDamping(PragmaDamping { qubit: 0, gate_time: Float(1.0), rate: Float(0.1) })\n",
-      "PragmaRepeatedMeasurement(PragmaRepeatedMeasurement { readout: \"ro\", qubit_mapping: None, number_measurements: 100 })\n",
-      "\n",
-      "Scaled result [0.86 1.  ]\n"
-     ]
-    }
-   ],
+   "execution_count": null,
    "source": [
     "from qoqo_pyquest import PyQuestBackend\n",
     "from qoqo import Circuit\n",
@@ -291,37 +268,62 @@
     "print(\"Scaled result\", scaled_result)\n",
     "\n",
     "assert len(scaled_result) == 2"
-   ]
+   ],
+   "outputs": [
+    {
+     "output_type": "stream",
+     "name": "stdout",
+     "text": [
+      "DefinitionBit(DefinitionBit { name: \"ro\", length: 2, is_output: true })\n",
+      "PauliX(PauliX { qubit: 0 })\n",
+      "PauliX(PauliX { qubit: 1 })\n",
+      "PragmaDamping(PragmaDamping { qubit: 0, gate_time: Float(1.0), rate: Float(0.1) })\n",
+      "PragmaRepeatedMeasurement(PragmaRepeatedMeasurement { readout: \"ro\", qubit_mapping: None, number_measurements: 100 })\n",
+      "\n",
+      "Scaled result [0.86 1.  ]\n"
+     ]
+    }
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "markdown",
-   "id": "prostate-analysis",
-   "metadata": {},
    "source": [
     "## Symbolic parameters\n",
     "In many cases, operation parameters depend on a symbolic parameter of the whole quantum program (time in time-evolution, overrotation, variational parameters...)  \n",
     "Qoqo allows the fast calculation of symbolic parameter expressions.  \n",
     "Expressions are provided in string form.  \n",
     "DoUnitary can automatically replace symbolic parameters using call parameters."
-   ]
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "markdown",
-   "id": "cross-forest",
-   "metadata": {},
    "source": [
     "### Writing the symbolic circuit and replacing symbolic parameters"
-   ]
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "code",
-   "execution_count": 6,
-   "id": "exposed-generation",
-   "metadata": {},
+   "execution_count": null,
+   "source": [
+    "from qoqo import Circuit\n",
+    "from qoqo import operations as ops\n",
+    "circuit = Circuit()\n",
+    "print('Symbolic circuit')\n",
+    "circuit += ops.RotateX(qubit=0, theta='3*time+offset')\n",
+    "\n",
+    "print(circuit)\n",
+    "\n",
+    "circuit2 = circuit.substitute_parameters({'time': 1/3, 'offset':1})\n",
+    "print('After substitution')\n",
+    "print(circuit2)\n"
+   ],
    "outputs": [
     {
-     "name": "stdout",
      "output_type": "stream",
+     "name": "stdout",
      "text": [
       "Symbolic circuit\n",
       "RotateX(RotateX { qubit: 0, theta: Str(\"3*time+offset\") })\n",
@@ -332,43 +334,18 @@
      ]
     }
    ],
-   "source": [
-    "from qoqo import Circuit\n",
-    "from qoqo import operations as ops\n",
-    "circuit = Circuit()\n",
-    "print('Symbolic circuit')\n",
-    "circuit += ops.RotateX(qubit=0, theta='3*time+offset')\n",
-    "\n",
-    "print(circuit)\n",
-    "\n",
-    "circuit2 = circuit.substitute_parameters({'time': 1/3, 'offset':1})\n",
-    "print('After substitution')\n",
-    "print(circuit2)\n"
-   ]
+   "metadata": {}
   },
   {
    "cell_type": "markdown",
-   "id": "talented-operations",
-   "metadata": {},
    "source": [
     "### Symbolic parameters in a full quantum program"
-   ]
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "code",
-   "execution_count": 7,
-   "id": "proof-lancaster",
-   "metadata": {},
-   "outputs": [
-    {
-     "name": "stdout",
-     "output_type": "stream",
-     "text": [
-      "{'time': 0.5, 'offset': 0}\n",
-      "Result {'example': 0.29, 'time': 0.5, 'offset': 0}\n"
-     ]
-    }
-   ],
+   "execution_count": null,
    "source": [
     "from qoqo.measurements import BasisRotationInput, BasisRotation\n",
     "from qoqo import DoUnitary\n",
@@ -399,35 +376,31 @@
     "print(\"Result\", result)\n",
     "\n",
     "assert len(result) == 3"
-   ]
+   ],
+   "outputs": [
+    {
+     "output_type": "stream",
+     "name": "stdout",
+     "text": [
+      "{'time': 0.5, 'offset': 0}\n",
+      "Result {'example': 0.29, 'time': 0.5, 'offset': 0}\n"
+     ]
+    }
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "markdown",
-   "id": "ready-benjamin",
-   "metadata": {},
    "source": [
     "## Testing scaling performance with qoqo_mock\n",
     "Quantum simulators cannot simulate systems with a significant number of qubits fast enough to benchmark qoqo with a large number of qubits and operations.\n",
     "The qoqo_mock interface can be used to benchmark qoqo without simulating a quantum computer."
-   ]
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "code",
-   "execution_count": 8,
-   "id": "independent-staff",
-   "metadata": {},
-   "outputs": [
-    {
-     "name": "stdout",
-     "output_type": "stream",
-     "text": [
-      "{'theta_x': 0, 'theta_y': 1, 'theta_z': 2}\n",
-      "Result {'example': -0.00324, 'theta_x': 0, 'theta_y': 1, 'theta_z': 2}\n",
-      "{'theta_x': 0, 'theta_y': 1, 'theta_z': 2}\n",
-      "Time taken 9.808817166999999\n"
-     ]
-    }
-   ],
+   "execution_count": null,
    "source": [
     "from qoqo.measurements import BasisRotationInput, BasisRotation\n",
     "from qoqo import DoUnitary\n",
@@ -455,7 +428,7 @@
     "    if i == 2:\n",
     "        circuit += ops.RotateZ(qubit=q, theta=\"3*theta_z\")\n",
     "    if i == 4:\n",
-    "        circuit += ops.ControlledPauliZ(qubit=q, control=0)\n",
+    "        circuit += ops.ControlledPauliZ(target=q, control=0)\n",
     "circuit += ops.PragmaRepeatedMeasurement(readout='ro', number_measurements=number_measurements, qubit_mapping=None)\n",
     "\n",
     "pp_dict = dict()\n",
@@ -478,22 +451,33 @@
     "\n",
     "assert len(res) == 4 \n",
     "assert time_taken < 30"
-   ]
+   ],
+   "outputs": [
+    {
+     "output_type": "stream",
+     "name": "stdout",
+     "text": [
+      "{'theta_x': 0, 'theta_y': 1, 'theta_z': 2}\n",
+      "Result {'example': -0.00324, 'theta_x': 0, 'theta_y': 1, 'theta_z': 2}\n",
+      "{'theta_x': 0, 'theta_y': 1, 'theta_z': 2}\n",
+      "Time taken 9.808817166999999\n"
+     ]
+    }
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "code",
    "execution_count": null,
-   "id": "buried-mention",
-   "metadata": {},
+   "source": [],
    "outputs": [],
-   "source": []
+   "metadata": {}
   }
  ],
  "metadata": {
   "kernelspec": {
-   "display_name": "Python 3",
-   "language": "python",
-   "name": "python3"
+   "name": "python3",
+   "display_name": "Python 3.8.3 64-bit ('base': conda)"
   },
   "language_info": {
    "codemirror_mode": {
@@ -505,9 +489,12 @@
    "name": "python",
    "nbconvert_exporter": "python",
    "pygments_lexer": "ipython3",
-   "version": "3.9.1"
+   "version": "3.8.3"
+  },
+  "interpreter": {
+   "hash": "dca0ade3e726a953b501b15e8e990130d2b7799f14cfd9f4271676035ebe5511"
   }
  },
  "nbformat": 4,
  "nbformat_minor": 5
-}
+}
\ No newline at end of file
diff --git a/qoqo/examples/Simple_VHA_with_qoqo.ipynb b/qoqo/examples/Simple_VHA_with_qoqo.ipynb
index 6003c633..493cbb67 100644
--- a/qoqo/examples/Simple_VHA_with_qoqo.ipynb
+++ b/qoqo/examples/Simple_VHA_with_qoqo.ipynb
@@ -2,8 +2,6 @@
  "cells": [
   {
    "cell_type": "markdown",
-   "id": "linear-albania",
-   "metadata": {},
    "source": [
     "# How to run a simple variational algorithm with qoqo\n",
     "\n",
@@ -11,12 +9,11 @@
     "The variational algorithm will be a very simple example of a Variational Hamiltonian Ansatz (VHA), the code does not aim to get the best result possible but to show a very simple example.\n",
     "\n",
     "For detailed discussions of variational algorithms, VHA and different variants of these algorithms see the literature (e.g. http://arxiv.org/abs/1304.3061, http://arxiv.org/abs/1509.04279).\n"
-   ]
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "markdown",
-   "id": "amber-jungle",
-   "metadata": {},
    "source": [
     "## Example: VHA for spins using qoqo\n",
     "\n",
@@ -54,12 +51,11 @@
     "$$\n",
     "H_2 = t \\sigma^x_1\\sigma^x_2.\n",
     "$$\n"
-   ]
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "markdown",
-   "id": "secondary-accused",
-   "metadata": {},
    "source": [
     "### The VHA example consists of the following steps:\n",
     "\n",
@@ -70,14 +66,12 @@
     "5. Use the compact DoUnitary quantum program to optimize the free parameters $\\vec{\\theta}$.\n",
     "\n",
     "Additionally, an exact solution of the Hamiltonian is presented at the end to compare the exact results with the calculated solution."
-   ]
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "code",
-   "execution_count": 1,
-   "id": "capable-dallas",
-   "metadata": {},
-   "outputs": [],
+   "execution_count": null,
    "source": [
     "# import standard python components\n",
     "import numpy as np\n",
@@ -96,14 +90,13 @@
     "# import modules and classes from qoqo for measuring observables\n",
     "from qoqo.measurements import BasisRotationInput, BasisRotation\n",
     "from qoqo import DoUnitary"
-   ]
+   ],
+   "outputs": [],
+   "metadata": {}
   },
   {
    "cell_type": "code",
-   "execution_count": 2,
-   "id": "banned-combat",
-   "metadata": {},
-   "outputs": [],
+   "execution_count": null,
    "source": [
     "# variables\n",
     "number_measurements = 10000\n",
@@ -113,12 +106,12 @@
     "# parameters\n",
     "magnetic_field = 1.0\n",
     "hopping_parameter = 3.0"
-   ]
+   ],
+   "outputs": [],
+   "metadata": {}
   },
   {
    "cell_type": "markdown",
-   "id": "marine-socket",
-   "metadata": {},
    "source": [
     "### 1. Initialization of the state vector by qoqo\n",
     "\n",
@@ -142,23 +135,12 @@
     "|\\psi_{\\textrm{init}}> =  \\frac{1}{\\sqrt{6}}|001> + \\frac{1}{\\sqrt{6}} |010> + \\frac{1}{\\sqrt{6}} |100> + \\frac{1}{\\sqrt{2}} |111>.\n",
     "$$\n",
     "We do not include extra terms to change the number of excitations in the VHA ansatz. Choosing a good initial guess for the number of excitations helps with convergence. For VHA variations that automatically derive the right number of excitations see for example https://doi.org/10.1088/2058-9565/abe568."
-   ]
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "code",
-   "execution_count": 3,
-   "id": "middle-emerald",
-   "metadata": {},
-   "outputs": [
-    {
-     "name": "stdout",
-     "output_type": "stream",
-     "text": [
-      "Step 1: Constructed initialization circuit.\n",
-      "        Number of qubits in the system:  3 .\n"
-     ]
-    }
-   ],
+   "execution_count": null,
    "source": [
     "initial_vector_array = np.array([0.0, 1/np.sqrt(6), 1/np.sqrt(6),0.0 ,1/np.sqrt(6), 0.0, 0.0, 1/np.sqrt(2)]) \n",
     "\n",
@@ -168,130 +150,23 @@
     "\n",
     "print('Step 1: Constructed initialization circuit.')\n",
     "print('        Number of qubits in the system: ', number_qubits, '.')"
-   ]
+   ],
+   "outputs": [],
+   "metadata": {}
   },
   {
    "cell_type": "markdown",
-   "id": "interesting-screw",
-   "metadata": {},
    "source": [
     "### 2. Unitary time evolution\n",
     "\n",
     "We construct circuits that apply time evolution under the even and odd hopping Hamiltonians and under the magnetic field using variables t (hopping_parameter) and B (magnetic_field).  \n",
     "For each iteration of the evolution we get free symbolic parameters theta_even_i, theta_odd_i and theta_z_i. "
-   ]
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "code",
-   "execution_count": 4,
-   "id": "impossible-civilization",
-   "metadata": {},
-   "outputs": [
-    {
-     "name": "stdout",
-     "output_type": "stream",
-     "text": [
-      "Step 2: Constructed evolution circuit.\n",
-      "Hadamard(Hadamard { qubit: 0 })\n",
-      "Hadamard(Hadamard { qubit: 1 })\n",
-      "CNOT(CNOT { control: 1, target: 0 })\n",
-      "RotateZ(RotateZ { qubit: 0, theta: Str(\"(theta_even_0 * 3e0)\") })\n",
-      "CNOT(CNOT { control: 1, target: 0 })\n",
-      "Hadamard(Hadamard { qubit: 0 })\n",
-      "Hadamard(Hadamard { qubit: 1 })\n",
-      "Hadamard(Hadamard { qubit: 1 })\n",
-      "Hadamard(Hadamard { qubit: 2 })\n",
-      "CNOT(CNOT { control: 2, target: 1 })\n",
-      "RotateZ(RotateZ { qubit: 1, theta: Str(\"(theta_odd_0 * 3e0)\") })\n",
-      "CNOT(CNOT { control: 2, target: 1 })\n",
-      "Hadamard(Hadamard { qubit: 1 })\n",
-      "Hadamard(Hadamard { qubit: 2 })\n",
-      "Hadamard(Hadamard { qubit: 2 })\n",
-      "Hadamard(Hadamard { qubit: 0 })\n",
-      "CNOT(CNOT { control: 0, target: 2 })\n",
-      "RotateZ(RotateZ { qubit: 2, theta: Str(\"(theta_odd_0 * 3e0)\") })\n",
-      "CNOT(CNOT { control: 0, target: 2 })\n",
-      "Hadamard(Hadamard { qubit: 2 })\n",
-      "Hadamard(Hadamard { qubit: 0 })\n",
-      "RotateZ(RotateZ { qubit: 0, theta: Str(\"theta_z_0\") })\n",
-      "RotateZ(RotateZ { qubit: 1, theta: Str(\"theta_z_0\") })\n",
-      "RotateZ(RotateZ { qubit: 2, theta: Str(\"theta_z_0\") })\n",
-      "Hadamard(Hadamard { qubit: 0 })\n",
-      "Hadamard(Hadamard { qubit: 1 })\n",
-      "CNOT(CNOT { control: 1, target: 0 })\n",
-      "RotateZ(RotateZ { qubit: 0, theta: Str(\"(theta_even_1 * 3e0)\") })\n",
-      "CNOT(CNOT { control: 1, target: 0 })\n",
-      "Hadamard(Hadamard { qubit: 0 })\n",
-      "Hadamard(Hadamard { qubit: 1 })\n",
-      "Hadamard(Hadamard { qubit: 1 })\n",
-      "Hadamard(Hadamard { qubit: 2 })\n",
-      "CNOT(CNOT { control: 2, target: 1 })\n",
-      "RotateZ(RotateZ { qubit: 1, theta: Str(\"(theta_odd_1 * 3e0)\") })\n",
-      "CNOT(CNOT { control: 2, target: 1 })\n",
-      "Hadamard(Hadamard { qubit: 1 })\n",
-      "Hadamard(Hadamard { qubit: 2 })\n",
-      "Hadamard(Hadamard { qubit: 2 })\n",
-      "Hadamard(Hadamard { qubit: 0 })\n",
-      "CNOT(CNOT { control: 0, target: 2 })\n",
-      "RotateZ(RotateZ { qubit: 2, theta: Str(\"(theta_odd_1 * 3e0)\") })\n",
-      "CNOT(CNOT { control: 0, target: 2 })\n",
-      "Hadamard(Hadamard { qubit: 2 })\n",
-      "Hadamard(Hadamard { qubit: 0 })\n",
-      "RotateZ(RotateZ { qubit: 0, theta: Str(\"theta_z_1\") })\n",
-      "RotateZ(RotateZ { qubit: 1, theta: Str(\"theta_z_1\") })\n",
-      "RotateZ(RotateZ { qubit: 2, theta: Str(\"theta_z_1\") })\n",
-      "Hadamard(Hadamard { qubit: 0 })\n",
-      "Hadamard(Hadamard { qubit: 1 })\n",
-      "CNOT(CNOT { control: 1, target: 0 })\n",
-      "RotateZ(RotateZ { qubit: 0, theta: Str(\"(theta_even_2 * 3e0)\") })\n",
-      "CNOT(CNOT { control: 1, target: 0 })\n",
-      "Hadamard(Hadamard { qubit: 0 })\n",
-      "Hadamard(Hadamard { qubit: 1 })\n",
-      "Hadamard(Hadamard { qubit: 1 })\n",
-      "Hadamard(Hadamard { qubit: 2 })\n",
-      "CNOT(CNOT { control: 2, target: 1 })\n",
-      "RotateZ(RotateZ { qubit: 1, theta: Str(\"(theta_odd_2 * 3e0)\") })\n",
-      "CNOT(CNOT { control: 2, target: 1 })\n",
-      "Hadamard(Hadamard { qubit: 1 })\n",
-      "Hadamard(Hadamard { qubit: 2 })\n",
-      "Hadamard(Hadamard { qubit: 2 })\n",
-      "Hadamard(Hadamard { qubit: 0 })\n",
-      "CNOT(CNOT { control: 0, target: 2 })\n",
-      "RotateZ(RotateZ { qubit: 2, theta: Str(\"(theta_odd_2 * 3e0)\") })\n",
-      "CNOT(CNOT { control: 0, target: 2 })\n",
-      "Hadamard(Hadamard { qubit: 2 })\n",
-      "Hadamard(Hadamard { qubit: 0 })\n",
-      "RotateZ(RotateZ { qubit: 0, theta: Str(\"theta_z_2\") })\n",
-      "RotateZ(RotateZ { qubit: 1, theta: Str(\"theta_z_2\") })\n",
-      "RotateZ(RotateZ { qubit: 2, theta: Str(\"theta_z_2\") })\n",
-      "Hadamard(Hadamard { qubit: 0 })\n",
-      "Hadamard(Hadamard { qubit: 1 })\n",
-      "CNOT(CNOT { control: 1, target: 0 })\n",
-      "RotateZ(RotateZ { qubit: 0, theta: Str(\"(theta_even_3 * 3e0)\") })\n",
-      "CNOT(CNOT { control: 1, target: 0 })\n",
-      "Hadamard(Hadamard { qubit: 0 })\n",
-      "Hadamard(Hadamard { qubit: 1 })\n",
-      "Hadamard(Hadamard { qubit: 1 })\n",
-      "Hadamard(Hadamard { qubit: 2 })\n",
-      "CNOT(CNOT { control: 2, target: 1 })\n",
-      "RotateZ(RotateZ { qubit: 1, theta: Str(\"(theta_odd_3 * 3e0)\") })\n",
-      "CNOT(CNOT { control: 2, target: 1 })\n",
-      "Hadamard(Hadamard { qubit: 1 })\n",
-      "Hadamard(Hadamard { qubit: 2 })\n",
-      "Hadamard(Hadamard { qubit: 2 })\n",
-      "Hadamard(Hadamard { qubit: 0 })\n",
-      "CNOT(CNOT { control: 0, target: 2 })\n",
-      "RotateZ(RotateZ { qubit: 2, theta: Str(\"(theta_odd_3 * 3e0)\") })\n",
-      "CNOT(CNOT { control: 0, target: 2 })\n",
-      "Hadamard(Hadamard { qubit: 2 })\n",
-      "Hadamard(Hadamard { qubit: 0 })\n",
-      "RotateZ(RotateZ { qubit: 0, theta: Str(\"theta_z_3\") })\n",
-      "RotateZ(RotateZ { qubit: 1, theta: Str(\"theta_z_3\") })\n",
-      "RotateZ(RotateZ { qubit: 2, theta: Str(\"theta_z_3\") })\n",
-      "\n"
-     ]
-    }
-   ],
+   "execution_count": null,
    "source": [
     "# variational evolution for the hopping terms\n",
     "def create_even_hopping_circuit(thetasymb: CalculatorFloat) -> Circuit:\n",
@@ -386,12 +261,12 @@
     "\n",
     "print('Step 2: Constructed evolution circuit.')\n",
     "print(circuit_evolution)"
-   ]
+   ],
+   "outputs": [],
+   "metadata": {}
   },
   {
    "cell_type": "markdown",
-   "id": "typical-contract",
-   "metadata": {},
    "source": [
     "### 3. Basis rotation (BR) measurement to get the expectation values\n",
     "\n",
@@ -399,33 +274,12 @@
     "The magnetic field part of the Hamiltonian contains only $\\sigma^z$ operators and can be measured in the z-basis of all qubits. The hopping parts of the Hamiltonian contain only products of $\\sigma^x$ operators and can be measured in the x-basis of all qubits. For more information on the basis rotation measurement see the \"Introduction to qoqo\" example.  \n",
     "\n",
     "After constructing the measurement circuit and the measurement information we combine everything into one qoqo measurement."
-   ]
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "code",
-   "execution_count": 5,
-   "id": "generous-voluntary",
-   "metadata": {},
-   "outputs": [
-    {
-     "name": "stdout",
-     "output_type": "stream",
-     "text": [
-      "Step 3: Measurement circuits constructed.\n",
-      "z-basis: \n",
-      "DefinitionBit(DefinitionBit { name: \"ro_z\", length: 3, is_output: true })\n",
-      "PragmaRepeatedMeasurement(PragmaRepeatedMeasurement { readout: \"ro_z\", qubit_mapping: None, number_measurements: 10000 })\n",
-      "\n",
-      "x-basis: \n",
-      "DefinitionBit(DefinitionBit { name: \"ro_x\", length: 3, is_output: true })\n",
-      "Hadamard(Hadamard { qubit: 0 })\n",
-      "Hadamard(Hadamard { qubit: 1 })\n",
-      "Hadamard(Hadamard { qubit: 2 })\n",
-      "PragmaRepeatedMeasurement(PragmaRepeatedMeasurement { readout: \"ro_x\", qubit_mapping: None, number_measurements: 10000 })\n",
-      "\n"
-     ]
-    }
-   ],
+   "execution_count": null,
    "source": [
     "# Setting up two basis rotation measurement circuits since we need to measure in two different bases\n",
     "x_basis_measurement_circuit = Circuit()\n",
@@ -462,8 +316,8 @@
     "# Adding the linear combinations of Pauli products that give the expectation values\n",
     "measurement_input.add_linear_exp_val(\n",
     "    name=\"energy\",\n",
-    "    linear={0:magnetic_field, 1:magnetic_field, 2:magnetic_field,\n",
-    "            3:hopping_parameter, 4:hopping_parameter, 5:hopping_parameter\n",
+    "    linear={index0: magnetic_field, index1: magnetic_field, index2: magnetic_field,\n",
+    "            index3: hopping_parameter, index4: hopping_parameter, index5: hopping_parameter\n",
     "           })\n",
     "\n",
     "print('Step 3: Measurement circuits constructed.')\n",
@@ -471,38 +325,27 @@
     "print(z_basis_measurement_circuit)\n",
     "print('x-basis: ')\n",
     "print(x_basis_measurement_circuit)"
-   ]
+   ],
+   "outputs": [],
+   "metadata": {}
   },
   {
    "cell_type": "markdown",
-   "id": "worth-motor",
-   "metadata": {},
    "source": [
     "### 4. Combining the parts to DoUnitary\n",
     "\n",
     "To execute the optimization we combine all the constructed circuits and put them in one qoqo DoUnitary quantum programm. With DoUnitary we only need to provide the free parameters and get back the measured expectation values."
-   ]
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "code",
-   "execution_count": 6,
-   "id": "together-index",
-   "metadata": {},
-   "outputs": [
-    {
-     "name": "stdout",
-     "output_type": "stream",
-     "text": [
-      "Step 4: DoUnitary constructed.\n"
-     ]
-    }
-   ],
+   "execution_count": null,
    "source": [
     "# Construct basis rotation measurement to get the expectation values\n",
     "measurement = BasisRotation(input=measurement_input, \n",
     "                            circuits=[circuit_init + circuit_evolution + z_basis_measurement_circuit,\n",
-    "                                       circuit_init + circuit_evolution + x_basis_measurement_circuit\n",
-    "                                     ],\n",
+    "                            circuit_init + circuit_evolution + x_basis_measurement_circuit],\n",
     "                            constant_circuit=None)  \n",
     "\n",
     "# one needs to define a backend where the program is executed\n",
@@ -518,161 +361,21 @@
     "                     ])\n",
     "\n",
     "print('Step 4: DoUnitary constructed.')"
-   ]
+   ],
+   "outputs": [],
+   "metadata": {}
   },
   {
    "cell_type": "markdown",
-   "id": "parliamentary-statistics",
-   "metadata": {},
    "source": [
     "### 5. Optimization of free parameters\n",
     "Minimiization routine to optimize the free parameters. This quantum program has 12 free parameters: theta_even, theta_odd and theta_z for each of the 4 iterations of evolution."
-   ]
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "code",
-   "execution_count": 7,
-   "id": "dedicated-plane",
-   "metadata": {},
-   "outputs": [
-    {
-     "name": "stdout",
-     "output_type": "stream",
-     "text": [
-      "7.228000000000001\n",
-      "8.5448\n",
-      "8.5476\n",
-      "-0.21920000000000006\n",
-      "1.3324000000000003\n",
-      "1.1623999999999999\n",
-      "-1.2975999999999999\n",
-      "-0.20839999999999997\n",
-      "-0.07559999999999995\n",
-      "6.952000000000001\n",
-      "-0.2228\n",
-      "-0.07200000000000001\n",
-      "6.989599999999999\n",
-      "2.0444000000000004\n",
-      "-2.508\n",
-      "-2.1756\n",
-      "-0.5831999999999998\n",
-      "-0.9044\n",
-      "-4.0084\n",
-      "-1.5652\n",
-      "-4.93\n",
-      "-2.8216\n",
-      "-4.144399999999999\n",
-      "-2.4188\n",
-      "-3.976\n",
-      "-3.8596000000000004\n",
-      "-4.851999999999999\n",
-      "0.6644000000000003\n",
-      "-5.0164\n",
-      "-3.1104000000000003\n",
-      "-3.8716\n",
-      "2.4320000000000004\n",
-      "-4.4876000000000005\n",
-      "-4.8108\n",
-      "-3.5248\n",
-      "-5.0728\n",
-      "-3.8912000000000004\n",
-      "-4.598\n",
-      "-5.1808\n",
-      "-4.202\n",
-      "-5.159599999999999\n",
-      "-4.9228\n",
-      "-5.0931999999999995\n",
-      "-4.7136\n",
-      "-5.212000000000001\n",
-      "-4.87\n",
-      "-5.19\n",
-      "-4.9628\n",
-      "-5.1468\n",
-      "-4.902400000000001\n",
-      "-5.0836\n",
-      "-4.724399999999999\n",
-      "-5.037599999999999\n",
-      "-5.1415999999999995\n",
-      "-5.1428\n",
-      "-5.112\n",
-      "-5.1895999999999995\n",
-      "-5.1884\n",
-      "-5.1432\n",
-      "-5.1784\n",
-      "-5.1604\n",
-      "-5.1592\n",
-      "-5.166\n",
-      "-5.1836\n",
-      "-5.1784\n",
-      "-5.204000000000001\n",
-      "-5.1972000000000005\n",
-      "-5.1728000000000005\n",
-      "-5.191599999999999\n",
-      "-5.1768\n",
-      "-5.191199999999999\n",
-      "-5.135199999999999\n",
-      "-5.194800000000001\n",
-      "-5.1852\n",
-      "-5.212400000000001\n",
-      "-5.2024\n",
-      "-5.1936\n",
-      "-5.1584\n",
-      "-5.1676\n",
-      "-5.1452\n",
-      "-5.231599999999999\n",
-      "-5.194000000000001\n",
-      "-5.2036\n",
-      "-5.1579999999999995\n",
-      "-5.167999999999999\n",
-      "-5.2012\n",
-      "-5.1892\n",
-      "-5.166799999999999\n",
-      "-5.1592\n",
-      "-5.1968000000000005\n",
-      "-5.1532\n",
-      "-5.2128000000000005\n",
-      "-5.180000000000001\n",
-      "-5.212000000000001\n",
-      "-5.176\n",
-      "-5.172\n",
-      "-5.1408000000000005\n",
-      "-5.1912\n",
-      "-5.1772\n",
-      "-5.1824\n",
-      "-5.154\n",
-      "-5.1368\n",
-      "-5.1884\n",
-      "-5.156000000000001\n",
-      "-5.193199999999999\n",
-      "-5.1456\n",
-      "-5.234\n",
-      "-5.178\n",
-      "-5.2052\n",
-      "-5.2144\n",
-      "-5.1644000000000005\n",
-      "-5.162000000000001\n",
-      "-5.216\n",
-      "-5.1656\n",
-      "-5.194399999999999\n",
-      "-5.2308\n",
-      "-5.1916\n",
-      "-5.183199999999999\n",
-      "-5.1636\n",
-      "-5.1932\n",
-      "-5.1968\n",
-      "-5.1952\n",
-      "-5.1432\n",
-      "-5.1916\n",
-      "-5.1768\n",
-      "-5.1788\n",
-      "-5.1932\n",
-      "-5.215199999999999\n",
-      "==> Optimized parameters theta:  [-0.17993992 -0.24339385  1.28551318 -0.21150318 -0.27625379  1.19704076\n",
-      " -0.07628173 -0.04542378 -0.08116322 -0.02755573 -0.03313859 -0.24759553] .\n",
-      "==> Calculated approximate Energy value:  -5.215199999999999 .\n"
-     ]
-    }
-   ],
+   "execution_count": null,
    "source": [
     "# \n",
     "def do_measurement(theta: List[float]) -> float:\n",
@@ -697,34 +400,22 @@
     "\n",
     "print('==> Optimized parameters theta: ', final_result.x, '.')\n",
     "print('==> Calculated approximate Energy value: ', final_result.fun, '.')"
-   ]
+   ],
+   "outputs": [],
+   "metadata": {}
   },
   {
    "cell_type": "markdown",
-   "id": "prostate-analysis",
-   "metadata": {},
    "source": [
     "## PART II: Compare the calculated (approximate) result to the exact classical solution\n",
     "\n",
     "Here we present an exact solution of the sample Hamiltonian to compare the exact results to the calculated solution of the VHA method."
-   ]
+   ],
+   "metadata": {}
   },
   {
    "cell_type": "code",
-   "execution_count": 8,
-   "id": "exposed-generation",
-   "metadata": {},
-   "outputs": [
-    {
-     "name": "stdout",
-     "output_type": "stream",
-     "text": [
-      "Step 4: Diagonalization of the classical Hamiltonian.\n",
-      "==> Energy of the ground state:  -5.2111 .\n",
-      "Difference between VHA result and exact result:  -0.0041 .\n"
-     ]
-    }
-   ],
+   "execution_count": null,
    "source": [
     "# fist, define Hamiltonian\n",
     "# pauli matrices\n",
@@ -756,22 +447,25 @@
     "# final print-out\n",
     "delta = final_result.fun - eigenvalues.real[0]\n",
     "print('Difference between VHA result and exact result: ', \"%.4f\" % delta, '.')"
-   ]
+   ],
+   "outputs": [],
+   "metadata": {}
   },
   {
    "cell_type": "code",
    "execution_count": null,
-   "id": "valuable-opportunity",
-   "metadata": {},
+   "source": [],
    "outputs": [],
-   "source": []
+   "metadata": {}
   }
  ],
  "metadata": {
+  "interpreter": {
+   "hash": "dca0ade3e726a953b501b15e8e990130d2b7799f14cfd9f4271676035ebe5511"
+  },
   "kernelspec": {
-   "display_name": "Python 3",
-   "language": "python",
-   "name": "python3"
+   "name": "python3",
+   "display_name": "Python 3.8.3 64-bit ('base': conda)"
   },
   "language_info": {
    "codemirror_mode": {
@@ -783,7 +477,7 @@
    "name": "python",
    "nbconvert_exporter": "python",
    "pygments_lexer": "ipython3",
-   "version": "3.9.1"
+   "version": "3.8.3"
   },
   "metadata": {
    "interpreter": {
@@ -793,4 +487,4 @@
  },
  "nbformat": 4,
  "nbformat_minor": 5
-}
+}
\ No newline at end of file
diff --git a/qoqo/src/operations/_auto_generated_operation_conversion.rs b/qoqo/src/operations/_auto_generated_operation_conversion.rs
index 1c766faa..44785150 100644
--- a/qoqo/src/operations/_auto_generated_operation_conversion.rs
+++ b/qoqo/src/operations/_auto_generated_operation_conversion.rs
@@ -34,6 +34,18 @@ pub fn convert_operation_to_pyobject(operation: Operation) -> PyResult<PyObject>
                 let pyobject: PyObject = pyref.to_object(py);
                 Ok(pyobject)
             }
+            Operation::PhaseShiftState1(internal) => {
+                let pyref: Py<PhaseShiftState1Wrapper> =
+                    Py::new(py, PhaseShiftState1Wrapper { internal }).unwrap();
+                let pyobject: PyObject = pyref.to_object(py);
+                Ok(pyobject)
+            }
+            Operation::PhaseShiftState0(internal) => {
+                let pyref: Py<PhaseShiftState0Wrapper> =
+                    Py::new(py, PhaseShiftState0Wrapper { internal }).unwrap();
+                let pyobject: PyObject = pyref.to_object(py);
+                Ok(pyobject)
+            }
             Operation::PauliX(internal) => {
                 let pyref: Py<PauliXWrapper> = Py::new(py, PauliXWrapper { internal }).unwrap();
                 let pyobject: PyObject = pyref.to_object(py);
@@ -462,6 +474,34 @@ pub fn convert_pyany_to_operation(op: &PyAny) -> Result<Operation, QoqoError> {
                 .map_err(|_| QoqoError::ConversionError)?;
             Ok(RotateZ::new(qubit, theta).into())
         }
+        "PhaseShiftState1" => {
+            let qubit_pyobject = op
+                .call_method0("qubit")
+                .map_err(|_| QoqoError::ConversionError)?;
+            let qubit: usize = qubit_pyobject
+                .extract()
+                .map_err(|_| QoqoError::ConversionError)?;
+            let theta_pyobject = op
+                .call_method0("theta")
+                .map_err(|_| QoqoError::ConversionError)?;
+            let theta = convert_into_calculator_float(theta_pyobject)
+                .map_err(|_| QoqoError::ConversionError)?;
+            Ok(PhaseShiftState1::new(qubit, theta).into())
+        }
+        "PhaseShiftState0" => {
+            let qubit_pyobject = op
+                .call_method0("qubit")
+                .map_err(|_| QoqoError::ConversionError)?;
+            let qubit: usize = qubit_pyobject
+                .extract()
+                .map_err(|_| QoqoError::ConversionError)?;
+            let theta_pyobject = op
+                .call_method0("theta")
+                .map_err(|_| QoqoError::ConversionError)?;
+            let theta = convert_into_calculator_float(theta_pyobject)
+                .map_err(|_| QoqoError::ConversionError)?;
+            Ok(PhaseShiftState0::new(qubit, theta).into())
+        }
         "PauliX" => {
             let qubit_pyobject = op
                 .call_method0("qubit")
diff --git a/qoqo/src/operations/mod.rs b/qoqo/src/operations/mod.rs
index f2a6bce6..81183239 100644
--- a/qoqo/src/operations/mod.rs
+++ b/qoqo/src/operations/mod.rs
@@ -173,6 +173,8 @@ pub fn operations(_py: Python, m: &PyModule) -> PyResult<()> {
     m.add_class::<PMInteractionWrapper>()?;
     m.add_class::<ComplexPMInteractionWrapper>()?;
     m.add_class::<PhaseShiftedControlledZWrapper>()?;
+    m.add_class::<PhaseShiftState0Wrapper>()?;
+    m.add_class::<PhaseShiftState1Wrapper>()?;
 
     Ok(())
 }
diff --git a/qoqo/src/operations/single_qubit_gate_operations.rs b/qoqo/src/operations/single_qubit_gate_operations.rs
index e8733b33..28c78c7a 100644
--- a/qoqo/src/operations/single_qubit_gate_operations.rs
+++ b/qoqo/src/operations/single_qubit_gate_operations.rs
@@ -132,6 +132,58 @@ struct RotateZ {
     theta: CalculatorFloat,
 }
 
+#[wrap(
+    Operate,
+    OperateSingleQubit,
+    Rotate,
+    OperateGate,
+    OperateSingleQubitGate
+)]
+/// The phase shift gate applied on state |1>.
+///
+/// Rotation around Z-axis by an arbitrary angle $\theta$ (AC Stark shift of the state |1>).
+///
+/// .. math::
+///     U = \begin{pmatrix}
+///         1 & 0\\\\
+///         0 & e^{i \theta}
+///         \end{pmatrix}
+///
+/// Args:
+///     qubit (int): The qubit the unitary gate is applied to.
+///     theta (CalculatorFloat): The angle :math:`\theta` of the rotation.
+///
+struct PhaseShiftState1 {
+    qubit: usize,
+    theta: CalculatorFloat,
+}
+
+#[wrap(
+    Operate,
+    OperateSingleQubit,
+    Rotate,
+    OperateGate,
+    OperateSingleQubitGate
+)]
+/// The phase shift gate applied on state |0>.
+///
+/// Rotation around Z-axis by an arbitrary angle $\theta$ (AC Stark shift of the state |0>).
+///
+/// .. math::
+///     U = \begin{pmatrix}
+///         e^{i \theta} & 0\\\\
+///         0 & 1
+///         \end{pmatrix}
+///
+/// Args:
+///     qubit (int): The qubit the unitary gate is applied to.
+///     theta (CalculatorFloat): The angle :math:`\theta` of the rotation.
+///
+struct PhaseShiftState0 {
+    qubit: usize,
+    theta: CalculatorFloat,
+}
+
 #[wrap(Operate, OperateSingleQubit, OperateGate, OperateSingleQubitGate)]
 /// The Pauli X gate.
 ///
diff --git a/roqoqo/src/circuit.rs b/roqoqo/src/circuit.rs
index 04f99254..acd3fa10 100644
--- a/roqoqo/src/circuit.rs
+++ b/roqoqo/src/circuit.rs
@@ -218,9 +218,7 @@ impl Circuit {
                     return InvolvedQubits::All;
                 }
                 InvolvedQubits::None => (),
-                InvolvedQubits::Set(x) => {
-                    temp_involved = temp_involved.union(&x).cloned().collect()
-                }
+                InvolvedQubits::Set(x) => temp_involved = temp_involved.union(x).cloned().collect(),
             }
         }
         match temp_involved.is_empty() {
diff --git a/roqoqo/src/operations/_auto_generated_operations.rs b/roqoqo/src/operations/_auto_generated_operations.rs
index 6b2f62f2..edbb19d7 100644
--- a/roqoqo/src/operations/_auto_generated_operations.rs
+++ b/roqoqo/src/operations/_auto_generated_operations.rs
@@ -40,6 +40,12 @@ pub enum Operation {
     #[doc = "Variant for TGate"]
     TGate(TGate),
     #[allow(clippy::upper_case_acronyms)]
+    #[doc = "Variant for PhaseShiftState1"]
+    PhaseShiftState1(PhaseShiftState1),
+    #[allow(clippy::upper_case_acronyms)]
+    #[doc = "Variant for PhaseShiftState0"]
+    PhaseShiftState0(PhaseShiftState0),
+    #[allow(clippy::upper_case_acronyms)]
     #[doc = "Variant for RotateAroundSphericalAxis"]
     RotateAroundSphericalAxis(RotateAroundSphericalAxis),
     #[allow(clippy::upper_case_acronyms)]
@@ -230,6 +236,10 @@ pub enum SingleQubitOperation {
     SGate(SGate),
     #[doc = "Variant for TGate"]
     TGate(TGate),
+    #[doc = "Variant for PhaseShiftState1"]
+    PhaseShiftState1(PhaseShiftState1),
+    #[doc = "Variant for PhaseShiftState0"]
+    PhaseShiftState0(PhaseShiftState0),
     #[doc = "Variant for RotateAroundSphericalAxis"]
     RotateAroundSphericalAxis(RotateAroundSphericalAxis),
     #[doc = "Variant for PragmaActiveReset"]
@@ -460,6 +470,12 @@ pub enum GateOperation {
     #[doc = "Variant for TGate"]
     TGate(TGate),
     #[allow(clippy::upper_case_acronyms)]
+    #[doc = "Variant for PhaseShiftState1"]
+    PhaseShiftState1(PhaseShiftState1),
+    #[allow(clippy::upper_case_acronyms)]
+    #[doc = "Variant for PhaseShiftState0"]
+    PhaseShiftState0(PhaseShiftState0),
+    #[allow(clippy::upper_case_acronyms)]
     #[doc = "Variant for RotateAroundSphericalAxis"]
     RotateAroundSphericalAxis(RotateAroundSphericalAxis),
     #[allow(clippy::upper_case_acronyms)]
@@ -547,6 +563,10 @@ pub enum Rotation {
     RotateX(RotateX),
     #[doc = "Variant for RotateY"]
     RotateY(RotateY),
+    #[doc = "Variant for PhaseShiftState1"]
+    PhaseShiftState1(PhaseShiftState1),
+    #[doc = "Variant for PhaseShiftState0"]
+    PhaseShiftState0(PhaseShiftState0),
     #[doc = "Variant for RotateAroundSphericalAxis"]
     RotateAroundSphericalAxis(RotateAroundSphericalAxis),
     #[doc = "Variant for XY"]
@@ -630,6 +650,10 @@ pub enum SingleQubitGateOperation {
     SGate(SGate),
     #[doc = "Variant for TGate"]
     TGate(TGate),
+    #[doc = "Variant for PhaseShiftState1"]
+    PhaseShiftState1(PhaseShiftState1),
+    #[doc = "Variant for PhaseShiftState0"]
+    PhaseShiftState0(PhaseShiftState0),
     #[doc = "Variant for RotateAroundSphericalAxis"]
     RotateAroundSphericalAxis(RotateAroundSphericalAxis),
 }
diff --git a/roqoqo/src/operations/single_qubit_gate_operations.rs b/roqoqo/src/operations/single_qubit_gate_operations.rs
index 724d097b..e909864d 100644
--- a/roqoqo/src/operations/single_qubit_gate_operations.rs
+++ b/roqoqo/src/operations/single_qubit_gate_operations.rs
@@ -1212,6 +1212,210 @@ impl OperateSingleQubitGate for TGate {
     }
 }
 
+/// The phase shift gate applied on state |1>.
+///
+/// Rotation around Z-axis by an arbitrary angle $\theta$ (AC Stark shift of the state |1>).
+///
+/// $$
+/// U = \begin{pmatrix}
+/// 1 & 0\\\\
+///  0 & e^{i \theta}
+/// \end{pmatrix}
+/// $$
+///
+#[derive(
+    Debug,
+    Clone,
+    PartialEq,
+    roqoqo_derive::InvolveQubits,
+    roqoqo_derive::Operate,
+    roqoqo_derive::Substitute,
+    roqoqo_derive::OperateSingleQubit,
+    roqoqo_derive::Rotate,
+)]
+#[cfg_attr(feature = "serialize", derive(serde::Serialize, serde::Deserialize))]
+pub struct PhaseShiftState1 {
+    /// The qubit the unitary gate is applied to.
+    qubit: usize,
+    /// The angle $\theta$ of the rotation, in the interval from 0 to $2 \pi$.
+    theta: CalculatorFloat,
+}
+
+#[allow(non_upper_case_globals)]
+const TAGS_PhaseShiftState1: &[&str; 5] = &[
+    "Operation",
+    "GateOperation",
+    "SingleQubitGateOperation",
+    "Rotation",
+    "PhaseShiftState1",
+];
+
+/// Trait for all operations acting with a unitary gate on a set of qubits.
+impl OperateGate for PhaseShiftState1 {
+    /// Returns unitary matrix of the gate.
+    ///
+    /// # Returns
+    ///
+    /// * `Ok(Array2<Complex64>)` - The unitary matrix representation of the gate.
+    /// * `Err(RoqoqoError)` - The parameter conversion to f64 failed (here, not possible).
+    fn unitary_matrix(&self) -> Result<Array2<Complex64>, RoqoqoError> {
+        let theta: f64 = f64::try_from(self.theta().clone())?;
+        Ok(array![
+            [Complex64::new(1.0, 0.0), Complex64::new(0.0, 0.0)],
+            [
+                Complex64::new(0.0, 0.0),
+                Complex64::new(theta.cos(), theta.sin())
+            ]
+        ])
+    }
+}
+
+/// Trait for unitary operations acting on exactly one qubit.
+impl OperateSingleQubitGate for PhaseShiftState1 {
+    /// Returns the alpha_r parameter of the operation.
+    ///
+    /// # Returns
+    ///
+    /// * `alpha_r` - The real part $\alpha_r$ of the on-diagonal elements of the single-qubit unitary matrix.
+    fn alpha_r(&self) -> CalculatorFloat {
+        (self.theta().clone() / 2.0).cos()
+    }
+    /// Returns the alpha_i parameter of the operation.
+    ///
+    /// # Returns
+    ///
+    /// * `alpha_i` - The imaginary part $ \alpha_i $ of the on-diagonal elements of the single-qubit unitary matrix.
+    fn alpha_i(&self) -> CalculatorFloat {
+        (self.theta().clone() / 2.0).sin() * (-1.0)
+    }
+    /// Returns the beta_r parameter of the operation.
+    ///
+    /// # Returns
+    ///
+    /// * `beta_r` - The real part $ \beta_r $ of the off-diagonal elements of the single-qubit unitary matrix.
+    fn beta_r(&self) -> CalculatorFloat {
+        CalculatorFloat::from(0.0)
+    }
+    /// Returns the beta_i parameter of the operation.
+    ///
+    /// # Returns
+    ///
+    /// * `beta_i` - The imaginary part $ \beta_i $ of the off-diagonal elements of the single-qubit unitary matrix.
+    fn beta_i(&self) -> CalculatorFloat {
+        CalculatorFloat::from(0.0)
+    }
+    /// Returns global_phase parameter of the operation.
+    ///
+    /// # Returns
+    ///
+    /// * `global_phase` - The global phase phi $ \phi $ of the single-qubit unitary.
+    fn global_phase(&self) -> CalculatorFloat {
+        self.theta().clone() / 2.0
+    }
+}
+
+/// The phase shift gate applied on state |0>.
+///
+/// Rotation around Z-axis by an arbitrary angle $\theta$ (AC Stark shift of the state |0>).
+///
+/// $$
+/// U = \begin{pmatrix}
+/// e^{i \theta} & 0\\\\
+///  0 & 1
+/// \end{pmatrix}
+/// $$
+///
+#[derive(
+    Debug,
+    Clone,
+    PartialEq,
+    roqoqo_derive::InvolveQubits,
+    roqoqo_derive::Operate,
+    roqoqo_derive::Substitute,
+    roqoqo_derive::OperateSingleQubit,
+    roqoqo_derive::Rotate,
+)]
+#[cfg_attr(feature = "serialize", derive(serde::Serialize, serde::Deserialize))]
+pub struct PhaseShiftState0 {
+    /// The qubit the unitary gate is applied to.
+    qubit: usize,
+    /// The angle $\theta$ of the rotation, in the interval from 0 to $2 \pi$.
+    theta: CalculatorFloat,
+}
+
+#[allow(non_upper_case_globals)]
+const TAGS_PhaseShiftState0: &[&str; 5] = &[
+    "Operation",
+    "GateOperation",
+    "SingleQubitGateOperation",
+    "Rotation",
+    "PhaseShiftState0",
+];
+
+/// Trait for all operations acting with a unitary gate on a set of qubits.
+impl OperateGate for PhaseShiftState0 {
+    /// Returns unitary matrix of the gate.
+    ///
+    /// # Returns
+    ///
+    /// * `Ok(Array2<Complex64>)` - The unitary matrix representation of the gate.
+    /// * `Err(RoqoqoError)` - The parameter conversion to f64 failed (here, not possible).
+    fn unitary_matrix(&self) -> Result<Array2<Complex64>, RoqoqoError> {
+        let theta: f64 = f64::try_from(self.theta().clone())?;
+        Ok(array![
+            [
+                Complex64::new(theta.cos(), theta.sin()),
+                Complex64::new(0.0, 0.0)
+            ],
+            [Complex64::new(0.0, 0.0), Complex64::new(1.0, 0.0)]
+        ])
+    }
+}
+
+/// Trait for unitary operations acting on exactly one qubit.
+impl OperateSingleQubitGate for PhaseShiftState0 {
+    /// Returns the alpha_r parameter of the operation.
+    ///
+    /// # Returns
+    ///
+    /// * `alpha_r` - The real part $\alpha_r$ of the on-diagonal elements of the single-qubit unitary matrix.
+    fn alpha_r(&self) -> CalculatorFloat {
+        (self.theta().clone() / 2.0).cos()
+    }
+    /// Returns the alpha_i parameter of the operation.
+    ///
+    /// # Returns
+    ///
+    /// * `alpha_i` - The imaginary part $ \alpha_i $ of the on-diagonal elements of the single-qubit unitary matrix.
+    fn alpha_i(&self) -> CalculatorFloat {
+        (self.theta().clone() / 2.0).sin()
+    }
+    /// Returns the beta_r parameter of the operation.
+    ///
+    /// # Returns
+    ///
+    /// * `beta_r` - The real part $ \beta_r $ of the off-diagonal elements of the single-qubit unitary matrix.
+    fn beta_r(&self) -> CalculatorFloat {
+        CalculatorFloat::from(0.0)
+    }
+    /// Returns the beta_i parameter of the operation.
+    ///
+    /// # Returns
+    ///
+    /// * `beta_i` - The imaginary part $ \beta_i $ of the off-diagonal elements of the single-qubit unitary matrix.
+    fn beta_i(&self) -> CalculatorFloat {
+        CalculatorFloat::from(0.0)
+    }
+    /// Returns global_phase parameter of the operation.
+    ///
+    /// # Returns
+    ///
+    /// * `global_phase` - The global phase phi $ \phi $ of the single-qubit unitary.
+    fn global_phase(&self) -> CalculatorFloat {
+        self.theta().clone() / 2.0
+    }
+}
+
 /// Implements a rotation around an axis in the x-y plane in spherical coordinates.
 ///
 /// $$


Test patch:
diff --git a/qoqo/tests/integration/operations/single_qubit_gate_operations.rs b/qoqo/tests/integration/operations/single_qubit_gate_operations.rs
index 24b6f81f..3e1a4759 100644
--- a/qoqo/tests/integration/operations/single_qubit_gate_operations.rs
+++ b/qoqo/tests/integration/operations/single_qubit_gate_operations.rs
@@ -18,8 +18,9 @@ use pyo3::Python;
 use qoqo::operations::convert_operation_to_pyobject;
 use qoqo::operations::{
     HadamardWrapper, InvSqrtPauliXWrapper, PauliXWrapper, PauliYWrapper, PauliZWrapper,
-    RotateAroundSphericalAxisWrapper, RotateXWrapper, RotateYWrapper, RotateZWrapper, SGateWrapper,
-    SingleQubitGateWrapper, SqrtPauliXWrapper, TGateWrapper,
+    PhaseShiftState0Wrapper, PhaseShiftState1Wrapper, RotateAroundSphericalAxisWrapper,
+    RotateXWrapper, RotateYWrapper, RotateZWrapper, SGateWrapper, SingleQubitGateWrapper,
+    SqrtPauliXWrapper, TGateWrapper,
 };
 use qoqo_calculator::Calculator;
 use qoqo_calculator::CalculatorFloat;
@@ -532,6 +533,104 @@ fn test_new_rotatez(input_operation: Operation, arguments: (u32, f64), method: &
     );
 }
 
+#[test_case(Operation::from(PhaseShiftState0::new(1, CalculatorFloat::ZERO)), (1, 0.0,), "__eq__"; "PhaseShiftState0_eq")]
+#[test_case(Operation::from(PhaseShiftState0::new(1, CalculatorFloat::ZERO)), (0, 0.0,), "__ne__"; "PhaseShiftState0_ne")]
+fn test_new_phaseshiftstate0(input_operation: Operation, arguments: (u32, f64), method: &str) {
+    let operation = convert_operation_to_pyobject(input_operation).unwrap();
+    pyo3::prepare_freethreaded_python();
+    let gil = pyo3::Python::acquire_gil();
+    let py = gil.python();
+
+    // Basic initialisation, no errors
+    let operation_type = py.get_type::<PhaseShiftState0Wrapper>();
+    let operation_py = operation_type
+        .call1(arguments)
+        .unwrap()
+        .cast_as::<PyCell<PhaseShiftState0Wrapper>>()
+        .unwrap();
+
+    let comparison = bool::extract(
+        operation
+            .as_ref(py)
+            .call_method1(method, (operation_py,))
+            .unwrap(),
+    )
+    .unwrap();
+    assert!(comparison);
+
+    // Error initialisation
+    let result = operation_type.call1((0, vec!["fails"]));
+    let result_ref = result.as_ref();
+    assert!(result_ref.is_err());
+
+    // Testing PartialEq, Clone and Debug
+    let def_wrapper = operation_py.extract::<PhaseShiftState0Wrapper>().unwrap();
+    let new_op_diff = operation_type
+        .call1((2, 0.0))
+        .unwrap()
+        .cast_as::<PyCell<PhaseShiftState0Wrapper>>()
+        .unwrap();
+    let def_wrapper_diff = new_op_diff.extract::<PhaseShiftState0Wrapper>().unwrap();
+    let helper_ne: bool = def_wrapper_diff != def_wrapper.clone();
+    assert!(helper_ne);
+    let helper_eq: bool = def_wrapper == def_wrapper.clone();
+    assert!(helper_eq);
+
+    assert_eq!(
+        format!("{:?}", def_wrapper_diff),
+        "PhaseShiftState0Wrapper { internal: PhaseShiftState0 { qubit: 2, theta: Float(0.0) } }"
+    );
+}
+
+#[test_case(Operation::from(PhaseShiftState1::new(1, CalculatorFloat::ZERO)), (1, 0.0,), "__eq__"; "PhaseShiftState1_eq")]
+#[test_case(Operation::from(PhaseShiftState1::new(1, CalculatorFloat::ZERO)), (0, 0.0,), "__ne__"; "PhaseShiftState1_ne")]
+fn test_new_phaseshiftstate1(input_operation: Operation, arguments: (u32, f64), method: &str) {
+    let operation = convert_operation_to_pyobject(input_operation).unwrap();
+    pyo3::prepare_freethreaded_python();
+    let gil = pyo3::Python::acquire_gil();
+    let py = gil.python();
+
+    // Basic initialisation, no errors
+    let operation_type = py.get_type::<PhaseShiftState1Wrapper>();
+    let operation_py = operation_type
+        .call1(arguments)
+        .unwrap()
+        .cast_as::<PyCell<PhaseShiftState1Wrapper>>()
+        .unwrap();
+
+    let comparison = bool::extract(
+        operation
+            .as_ref(py)
+            .call_method1(method, (operation_py,))
+            .unwrap(),
+    )
+    .unwrap();
+    assert!(comparison);
+
+    // Error initialisation
+    let result = operation_type.call1((0, vec!["fails"]));
+    let result_ref = result.as_ref();
+    assert!(result_ref.is_err());
+
+    // Testing PartialEq, Clone and Debug
+    let def_wrapper = operation_py.extract::<PhaseShiftState1Wrapper>().unwrap();
+    let new_op_diff = operation_type
+        .call1((2, 0.0))
+        .unwrap()
+        .cast_as::<PyCell<PhaseShiftState1Wrapper>>()
+        .unwrap();
+    let def_wrapper_diff = new_op_diff.extract::<PhaseShiftState1Wrapper>().unwrap();
+    let helper_ne: bool = def_wrapper_diff != def_wrapper.clone();
+    assert!(helper_ne);
+    let helper_eq: bool = def_wrapper == def_wrapper.clone();
+    assert!(helper_eq);
+
+    assert_eq!(
+        format!("{:?}", def_wrapper_diff),
+        "PhaseShiftState1Wrapper { internal: PhaseShiftState1 { qubit: 2, theta: Float(0.0) } }"
+    );
+}
+
 #[test_case(Operation::from(
     RotateAroundSphericalAxis::new(
         1,
@@ -691,9 +790,9 @@ fn test_new_singlequbitgate(
 }
 
 /// Test is_parametrized() function for SingleQubitGate Operations
-#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from("theta"))); "RotateX float")]
-#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from("theta"))); "RotateY float")]
-#[test_case(Operation::from(RotateZ::new(1, CalculatorFloat::from("theta"))); "RotateZ float")]
+#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from("theta"))); "RotateX")]
+#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from("theta"))); "RotateY")]
+#[test_case(Operation::from(RotateZ::new(1, CalculatorFloat::from("theta"))); "RotateZ")]
 #[test_case(Operation::from(
     SingleQubitGate::new(
         0,
@@ -714,6 +813,8 @@ fn test_new_singlequbitgate(
         )
     ); "RotateAroundSphericalAxis")
 ]
+#[test_case(Operation::from(PhaseShiftState0::new(1, CalculatorFloat::from("theta"))); "PhaseShiftState0")]
+#[test_case(Operation::from(PhaseShiftState1::new(1, CalculatorFloat::from("theta"))); "PhaseShiftState1")]
 fn test_pyo3_is_parametrized(input_operation: Operation) {
     pyo3::prepare_freethreaded_python();
     let gil = pyo3::Python::acquire_gil();
@@ -729,9 +830,9 @@ fn test_pyo3_is_parametrized(input_operation: Operation) {
 }
 
 /// Test is_parametrized = false for SingleQubitGate Operations
-#[test_case(Operation::from(RotateZ::new(1, CalculatorFloat::from(1.3))); "RotateZ float")]
-#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from(0))); "RotateX float")]
-#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from(PI))); "RotateY float")]
+#[test_case(Operation::from(RotateZ::new(1, CalculatorFloat::from(1.3))); "RotateZ")]
+#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from(0))); "RotateX")]
+#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from(PI))); "RotateY")]
 #[test_case(Operation::from(
     SingleQubitGate::new(
         0,
@@ -760,6 +861,8 @@ fn test_pyo3_is_parametrized(input_operation: Operation) {
 #[test_case(Operation::from(SGate::new(1)); "SGate")]
 #[test_case(Operation::from(TGate::new(1)); "TGate")]
 #[test_case(Operation::from(Hadamard::new(3)); "Hadamard")]
+#[test_case(Operation::from(PhaseShiftState0::new(1, CalculatorFloat::from(0))); "PhaseShiftState0")]
+#[test_case(Operation::from(PhaseShiftState1::new(1, CalculatorFloat::from(0))); "PhaseShiftState1")]
 fn test_pyo3_is_not_parametrized(input_operation: Operation) {
     pyo3::prepare_freethreaded_python();
     let gil = pyo3::Python::acquire_gil();
@@ -788,6 +891,8 @@ fn test_pyo3_is_not_parametrized(input_operation: Operation) {
         )
     ); "RotateAroundSphericalAxis")
 ]
+#[test_case(CalculatorFloat::from(0), Operation::from(PhaseShiftState0::new(1, CalculatorFloat::from(0))); "PhaseShiftState0")]
+#[test_case(CalculatorFloat::from(0), Operation::from(PhaseShiftState1::new(1, CalculatorFloat::from(0))); "PhaseShiftState1")]
 fn test_pyo3_theta(theta: CalculatorFloat, input_operation: Operation) {
     pyo3::prepare_freethreaded_python();
     let gil = pyo3::Python::acquire_gil();
@@ -822,6 +927,8 @@ fn test_pyo3_theta(theta: CalculatorFloat, input_operation: Operation) {
 #[test_case(0, Operation::from(TGate::new(0)); "TGate")]
 #[test_case(0, Operation::from(SGate::new(0)); "SGate")]
 #[test_case(0, Operation::from(Hadamard::new(0)); "Hadamard")]
+#[test_case(1, Operation::from(PhaseShiftState0::new(1, CalculatorFloat::from(0))); "PhaseShiftState0")]
+#[test_case(1, Operation::from(PhaseShiftState1::new(1, CalculatorFloat::from(0))); "PhaseShiftState1")]
 fn test_pyo3_qubit(qubit: usize, input_operation: Operation) {
     pyo3::prepare_freethreaded_python();
     let gil = pyo3::Python::acquire_gil();
@@ -863,6 +970,8 @@ fn test_pyo3_qubit(qubit: usize, input_operation: Operation) {
         CalculatorFloat::from(0.0),
         CalculatorFloat::from(PI),
     )); "SingleQubitGate")]
+#[test_case("PhaseShiftState0", Operation::from(PhaseShiftState0::new(1, CalculatorFloat::from(0))); "PhaseShiftState0")]
+#[test_case("PhaseShiftState1", Operation::from(PhaseShiftState1::new(1, CalculatorFloat::from(0))); "PhaseShiftState1")]
 fn test_pyo3_hqslang(name: &'static str, input_operation: Operation) {
     pyo3::prepare_freethreaded_python();
     let gil = pyo3::Python::acquire_gil();
@@ -873,7 +982,7 @@ fn test_pyo3_hqslang(name: &'static str, input_operation: Operation) {
     assert_eq!(name_op, name.to_string());
 }
 
-/// Test RotateX tags() function for SingleQubitGate Operations
+/// Test tags() function for SingleQubitGate Operations
 #[test_case(
     Operation::from(RotateX::new(0, CalculatorFloat::from(0))),
     vec![
@@ -1009,6 +1118,26 @@ fn test_pyo3_hqslang(name: &'static str, input_operation: Operation) {
         "SingleQubitGate",
         ];
     "SingleQubitGate")]
+#[test_case(
+    Operation::from(PhaseShiftState0::new(0, CalculatorFloat::from(0))),
+    vec![
+        "Operation",
+        "GateOperation",
+        "SingleQubitGateOperation",
+        "Rotation",
+        "PhaseShiftState0",
+        ];
+    "PhaseShiftState0")]
+#[test_case(
+    Operation::from(PhaseShiftState1::new(0, CalculatorFloat::from(0))),
+    vec![
+        "Operation",
+        "GateOperation",
+        "SingleQubitGateOperation",
+        "Rotation",
+        "PhaseShiftState1",
+        ];
+    "PhaseShiftState1")]
 fn test_pyo3_tags(input_operation: Operation, tags: Vec<&str>) {
     pyo3::prepare_freethreaded_python();
     let gil = pyo3::Python::acquire_gil();
@@ -1023,9 +1152,9 @@ fn test_pyo3_tags(input_operation: Operation, tags: Vec<&str>) {
 }
 
 /// Test remap_qubits() function for SingleQubitGate Operations
-#[test_case(Operation::from(RotateZ::new(0, CalculatorFloat::from(1.3))); "RotateZ float")]
-#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from(0))); "RotateX float")]
-#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from(PI))); "RotateY float")]
+#[test_case(Operation::from(RotateZ::new(0, CalculatorFloat::from(1.3))); "RotateZ")]
+#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from(0))); "RotateX")]
+#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from(PI))); "RotateY")]
 #[test_case(Operation::from(
     SingleQubitGate::new(
         0,
@@ -1054,6 +1183,8 @@ fn test_pyo3_tags(input_operation: Operation, tags: Vec<&str>) {
 #[test_case(Operation::from(SGate::new(0)); "SGate")]
 #[test_case(Operation::from(TGate::new(0)); "TGate")]
 #[test_case(Operation::from(Hadamard::new(0)); "Hadamard")]
+#[test_case(Operation::from(PhaseShiftState0::new(0, CalculatorFloat::from(0))); "PhaseShiftState0")]
+#[test_case(Operation::from(PhaseShiftState1::new(0, CalculatorFloat::from(0))); "PhaseShiftState1")]
 fn test_pyo3_remapqubits(input_operation: Operation) {
     pyo3::prepare_freethreaded_python();
     let gil = pyo3::Python::acquire_gil();
@@ -1078,9 +1209,9 @@ fn test_pyo3_remapqubits(input_operation: Operation) {
 }
 
 // test remap_qubits() function returning an error.
-#[test_case(Operation::from(RotateZ::new(0, CalculatorFloat::from(1.3))); "RotateZ float")]
-#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from(0))); "RotateX float")]
-#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from(PI))); "RotateY float")]
+#[test_case(Operation::from(RotateZ::new(0, CalculatorFloat::from(1.3))); "RotateZ")]
+#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from(0))); "RotateX")]
+#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from(PI))); "RotateY")]
 #[test_case(Operation::from(
     SingleQubitGate::new(
         0,
@@ -1109,6 +1240,8 @@ fn test_pyo3_remapqubits(input_operation: Operation) {
 #[test_case(Operation::from(SGate::new(0)); "SGate")]
 #[test_case(Operation::from(TGate::new(0)); "TGate")]
 #[test_case(Operation::from(Hadamard::new(0)); "Hadamard")]
+#[test_case(Operation::from(PhaseShiftState0::new(0, CalculatorFloat::from(0))); "PhaseShiftState0")]
+#[test_case(Operation::from(PhaseShiftState1::new(0, CalculatorFloat::from(0))); "PhaseShiftState1")]
 fn test_pyo3_remapqubits_error(input_operation: Operation) {
     // preparation
     pyo3::prepare_freethreaded_python();
@@ -1123,9 +1256,9 @@ fn test_pyo3_remapqubits_error(input_operation: Operation) {
 }
 
 /// Test unitary_matrix() function for SingleQubitGate Operations
-#[test_case(Operation::from(RotateZ::new(1, CalculatorFloat::from(1.3))); "RotateZ float")]
-#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from(0))); "RotateX float")]
-#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from(PI))); "RotateY float")]
+#[test_case(Operation::from(RotateZ::new(1, CalculatorFloat::from(1.3))); "RotateZ")]
+#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from(0))); "RotateX")]
+#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from(PI))); "RotateY")]
 #[test_case(Operation::from(
     RotateAroundSphericalAxis::new(
         0,
@@ -1154,6 +1287,8 @@ fn test_pyo3_remapqubits_error(input_operation: Operation) {
         )
     ); "SingleQubitGate")
 ]
+#[test_case(Operation::from(PhaseShiftState0::new(0, CalculatorFloat::from(-1.0))); "PhaseShiftState0")]
+#[test_case(Operation::from(PhaseShiftState1::new(0, CalculatorFloat::from(2.3))); "PhaseShiftState1")]
 fn test_pyo3_unitarymatrix(input_operation: Operation) {
     pyo3::prepare_freethreaded_python();
     let gil = pyo3::Python::acquire_gil();
@@ -1174,9 +1309,9 @@ fn test_pyo3_unitarymatrix(input_operation: Operation) {
 }
 
 /// Test unitary_matrix() function for SingleQubitGate Operations for the error case
-#[test_case(Operation::from(RotateZ::new(1, CalculatorFloat::from("PI"))); "RotateZ float")]
-#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from("PI"))); "RotateX float")]
-#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from("PI"))); "RotateY float")]
+#[test_case(Operation::from(RotateZ::new(1, CalculatorFloat::from("PI"))); "RotateZ")]
+#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from("PI"))); "RotateX")]
+#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from("PI"))); "RotateY")]
 #[test_case(Operation::from(
     RotateAroundSphericalAxis::new(
         0,
@@ -1186,6 +1321,8 @@ fn test_pyo3_unitarymatrix(input_operation: Operation) {
         )
     ); "RotateAroundSphericalAxis")
 ]
+#[test_case(Operation::from(PhaseShiftState0::new(0, CalculatorFloat::from("PI"))); "PhaseShiftState0")]
+#[test_case(Operation::from(PhaseShiftState1::new(0, CalculatorFloat::from("PI"))); "PhaseShiftState1")]
 fn test_pyo3_unitarymatrix_error(input_operation: Operation) {
     pyo3::prepare_freethreaded_python();
     let gil = pyo3::Python::acquire_gil();
@@ -1230,9 +1367,9 @@ fn test_pyo3_unitarymatrix_singlequbitgate(input_operation: Operation) {
 }
 
 /// Test copy and deepcopy functions
-#[test_case(Operation::from(RotateZ::new(1, CalculatorFloat::from(1.3))); "RotateZ float")]
-#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from(0))); "RotateX float")]
-#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from(PI))); "RotateY float")]
+#[test_case(Operation::from(RotateZ::new(1, CalculatorFloat::from(1.3))); "RotateZ")]
+#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from(0))); "RotateX")]
+#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from(PI))); "RotateY")]
 #[test_case(Operation::from(
     SingleQubitGate::new(
         0,
@@ -1261,6 +1398,8 @@ fn test_pyo3_unitarymatrix_singlequbitgate(input_operation: Operation) {
 #[test_case(Operation::from(SGate::new(1)); "SGate")]
 #[test_case(Operation::from(TGate::new(1)); "TGate")]
 #[test_case(Operation::from(Hadamard::new(3)); "Hadamard")]
+#[test_case(Operation::from(PhaseShiftState0::new(0, CalculatorFloat::from(0.0))); "PhaseShiftState0")]
+#[test_case(Operation::from(PhaseShiftState1::new(0, CalculatorFloat::from(0.0))); "PhaseShiftState1")]
 fn test_pyo3_copy_deepcopy(input_operation: Operation) {
     pyo3::prepare_freethreaded_python();
     let gil = pyo3::Python::acquire_gil();
@@ -1289,9 +1428,9 @@ fn test_pyo3_copy_deepcopy(input_operation: Operation) {
 }
 
 /// Test alpha_r obtained via the python interface for SingleQubitGate Operations
-#[test_case(Operation::from(RotateZ::new(1, CalculatorFloat::from(1.3))); "RotateZ float")]
-#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from(0))); "RotateX float")]
-#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from(PI))); "RotateY float")]
+#[test_case(Operation::from(RotateZ::new(1, CalculatorFloat::from(1.3))); "RotateZ")]
+#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from(0))); "RotateX")]
+#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from(PI))); "RotateY")]
 #[test_case(Operation::from(
     SingleQubitGate::new(
         0,
@@ -1320,6 +1459,8 @@ fn test_pyo3_copy_deepcopy(input_operation: Operation) {
 #[test_case(Operation::from(SGate::new(1)); "SGate")]
 #[test_case(Operation::from(TGate::new(1)); "TGate")]
 #[test_case(Operation::from(Hadamard::new(3)); "Hadamard")]
+#[test_case(Operation::from(PhaseShiftState0::new(0, CalculatorFloat::from(0.0))); "PhaseShiftState0")]
+#[test_case(Operation::from(PhaseShiftState1::new(0, CalculatorFloat::from(0.0))); "PhaseShiftState1")]
 fn test_pyo3_alpha_r(input_operation: Operation) {
     pyo3::prepare_freethreaded_python();
     let gil = pyo3::Python::acquire_gil();
@@ -1342,9 +1483,9 @@ fn test_pyo3_alpha_r(input_operation: Operation) {
 }
 
 /// Test alpha_i obtained via the python interface for SingleQubitGate Operations
-#[test_case(Operation::from(RotateZ::new(1, CalculatorFloat::from(1.3))); "RotateZ float")]
-#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from(0))); "RotateX float")]
-#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from(PI))); "RotateY float")]
+#[test_case(Operation::from(RotateZ::new(1, CalculatorFloat::from(1.3))); "RotateZ")]
+#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from(0))); "RotateX")]
+#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from(PI))); "RotateY")]
 #[test_case(Operation::from(
     SingleQubitGate::new(
         0,
@@ -1373,6 +1514,8 @@ fn test_pyo3_alpha_r(input_operation: Operation) {
 #[test_case(Operation::from(SGate::new(1)); "SGate")]
 #[test_case(Operation::from(TGate::new(1)); "TGate")]
 #[test_case(Operation::from(Hadamard::new(3)); "Hadamard")]
+#[test_case(Operation::from(PhaseShiftState0::new(0, CalculatorFloat::from(0.0))); "PhaseShiftState0")]
+#[test_case(Operation::from(PhaseShiftState1::new(0, CalculatorFloat::from(0.0))); "PhaseShiftState1")]
 fn test_pyo3_alpha_i(input_operation: Operation) {
     pyo3::prepare_freethreaded_python();
     let gil = pyo3::Python::acquire_gil();
@@ -1395,9 +1538,9 @@ fn test_pyo3_alpha_i(input_operation: Operation) {
 }
 
 /// Test beta_r obtained via the python interface for SingleQubitGate Operations
-#[test_case(Operation::from(RotateZ::new(1, CalculatorFloat::from(1.3))); "RotateZ float")]
-#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from(0))); "RotateX float")]
-#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from(PI))); "RotateY float")]
+#[test_case(Operation::from(RotateZ::new(1, CalculatorFloat::from(1.3))); "RotateZ")]
+#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from(0))); "RotateX")]
+#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from(PI))); "RotateY")]
 #[test_case(Operation::from(
     SingleQubitGate::new(
         0,
@@ -1426,6 +1569,8 @@ fn test_pyo3_alpha_i(input_operation: Operation) {
 #[test_case(Operation::from(SGate::new(1)); "SGate")]
 #[test_case(Operation::from(TGate::new(1)); "TGate")]
 #[test_case(Operation::from(Hadamard::new(3)); "Hadamard")]
+#[test_case(Operation::from(PhaseShiftState0::new(0, CalculatorFloat::from(0.0))); "PhaseShiftState0")]
+#[test_case(Operation::from(PhaseShiftState1::new(0, CalculatorFloat::from(0.0))); "PhaseShiftState1")]
 fn test_pyo3_beta_r(input_operation: Operation) {
     pyo3::prepare_freethreaded_python();
     let gil = pyo3::Python::acquire_gil();
@@ -1448,9 +1593,9 @@ fn test_pyo3_beta_r(input_operation: Operation) {
 }
 
 /// Test beta_i obtained via the python interface for SingleQubitGate Operations
-#[test_case(Operation::from(RotateZ::new(1, CalculatorFloat::from(1.3))); "RotateZ float")]
-#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from(0))); "RotateX float")]
-#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from(PI))); "RotateY float")]
+#[test_case(Operation::from(RotateZ::new(1, CalculatorFloat::from(1.3))); "RotateZ")]
+#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from(0))); "RotateX")]
+#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from(PI))); "RotateY")]
 #[test_case(Operation::from(
     SingleQubitGate::new(
         0,
@@ -1479,6 +1624,8 @@ fn test_pyo3_beta_r(input_operation: Operation) {
 #[test_case(Operation::from(SGate::new(1)); "SGate")]
 #[test_case(Operation::from(TGate::new(1)); "TGate")]
 #[test_case(Operation::from(Hadamard::new(3)); "Hadamard")]
+#[test_case(Operation::from(PhaseShiftState0::new(0, CalculatorFloat::from(0.0))); "PhaseShiftState0")]
+#[test_case(Operation::from(PhaseShiftState1::new(0, CalculatorFloat::from(0.0))); "PhaseShiftState1")]
 fn test_pyo3_beta_i(input_operation: Operation) {
     pyo3::prepare_freethreaded_python();
     let gil = pyo3::Python::acquire_gil();
@@ -1501,9 +1648,9 @@ fn test_pyo3_beta_i(input_operation: Operation) {
 }
 
 /// Test global_phase obtained via the python interface for SingleQubitGate Operations
-#[test_case(Operation::from(RotateZ::new(1, CalculatorFloat::from(1.3))); "RotateZ float")]
-#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from(0))); "RotateX float")]
-#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from(PI))); "RotateY float")]
+#[test_case(Operation::from(RotateZ::new(1, CalculatorFloat::from(1.3))); "RotateZ")]
+#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from(0))); "RotateX")]
+#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from(PI))); "RotateY")]
 #[test_case(Operation::from(
     SingleQubitGate::new(
         0,
@@ -1532,6 +1679,8 @@ fn test_pyo3_beta_i(input_operation: Operation) {
 #[test_case(Operation::from(SGate::new(1)); "SGate")]
 #[test_case(Operation::from(TGate::new(1)); "TGate")]
 #[test_case(Operation::from(Hadamard::new(3)); "Hadamard")]
+#[test_case(Operation::from(PhaseShiftState0::new(0, CalculatorFloat::from(0.0))); "PhaseShiftState0")]
+#[test_case(Operation::from(PhaseShiftState1::new(0, CalculatorFloat::from(0.0))); "PhaseShiftState1")]
 fn test_pyo3_global_phase(input_operation: Operation) {
     pyo3::prepare_freethreaded_python();
     let gil = pyo3::Python::acquire_gil();
@@ -1621,6 +1770,14 @@ fn test_pyo3_global_phase(input_operation: Operation) {
             )
     ); "SingleQubitGate")
 ]
+#[test_case(
+    "PhaseShiftState0 { qubit: 0, theta: Float(0.0) }",
+    Operation::from(PhaseShiftState0::new(0, CalculatorFloat::from(0)));
+    "PhaseShiftState0")]
+#[test_case(
+    "PhaseShiftState1 { qubit: 0, theta: Float(0.0) }",
+    Operation::from(PhaseShiftState1::new(0, CalculatorFloat::from(0)));
+    "PhaseShiftState1")]
 fn test_pyo3_format_repr(format_repr: &str, input_operation: Operation) {
     pyo3::prepare_freethreaded_python();
     let gil = pyo3::Python::acquire_gil();
@@ -1689,6 +1846,8 @@ fn test_pyo3_substitute_parameters(input_operation: Operation) {
 #[test_case(Operation::from(RotateZ::new(1, CalculatorFloat::from("theta"))); "RotateZ")]
 #[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from("theta"))); "RotateX")]
 #[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from("theta"))); "RotateY")]
+#[test_case(Operation::from(PhaseShiftState0::new(0, CalculatorFloat::from("theta"))); "PhaseShiftState0")]
+#[test_case(Operation::from(PhaseShiftState1::new(0, CalculatorFloat::from("theta"))); "PhaseShiftState1")]
 fn test_pyo3_substitute_params_rotate(input_operation: Operation) {
     pyo3::prepare_freethreaded_python();
     let gil = pyo3::Python::acquire_gil();
@@ -1741,6 +1900,8 @@ fn test_pyo3_substitute_params_rotate(input_operation: Operation) {
         )
     ); "SingleQubitGate")
 ]
+#[test_case(Operation::from(PhaseShiftState0::new(0, CalculatorFloat::from("theta"))); "PhaseShiftState0")]
+#[test_case(Operation::from(PhaseShiftState1::new(0, CalculatorFloat::from("theta"))); "PhaseShiftState1")]
 fn test_pyo3_substitute_params_error(input_operation: Operation) {
     pyo3::prepare_freethreaded_python();
     let gil = pyo3::Python::acquire_gil();
@@ -1761,6 +1922,11 @@ fn test_pyo3_substitute_params_error(input_operation: Operation) {
 #[test_case(Operation::from(SGate::new(1)); "SGate")]
 #[test_case(Operation::from(TGate::new(1)); "TGate")]
 #[test_case(Operation::from(Hadamard::new(3)); "Hadamard")]
+#[test_case(Operation::from(PhaseShiftState0::new(0, CalculatorFloat::from(0))); "PhaseShiftState0")]
+#[test_case(Operation::from(PhaseShiftState1::new(0, CalculatorFloat::from(0))); "PhaseShiftState1")]
+#[test_case(Operation::from(RotateZ::new(1, CalculatorFloat::from(0))); "RotateZ")]
+#[test_case(Operation::from(RotateX::new(0, CalculatorFloat::from(0))); "RotateX")]
+#[test_case(Operation::from(RotateY::new(0, CalculatorFloat::from(0))); "RotateY")]
 fn test_ineffective_substitute_parameters(input_operation: Operation) {
     pyo3::prepare_freethreaded_python();
     let gil = pyo3::Python::acquire_gil();
@@ -1791,6 +1957,12 @@ fn test_ineffective_substitute_parameters(input_operation: Operation) {
 #[test_case(
     Operation::from(RotateX::new(1, CalculatorFloat::from(0.005))),
     Operation::from(RotateX::new(1, CalculatorFloat::from(0.005 * 1.5))); "RotateX")]
+#[test_case(
+    Operation::from(PhaseShiftState0::new(1, CalculatorFloat::from(0.005))),
+    Operation::from(PhaseShiftState0::new(1, CalculatorFloat::from(0.005 * 1.5))); "PhaseShiftState0")]
+#[test_case(
+    Operation::from(PhaseShiftState1::new(1, CalculatorFloat::from(0.005))),
+    Operation::from(PhaseShiftState1::new(1, CalculatorFloat::from(0.005 * 1.5))); "PhaseShiftState1")]
 #[test_case(
     Operation::from(
         RotateAroundSphericalAxis::new(
@@ -1901,6 +2073,12 @@ fn test_pyo3_rotate_powercf(first_op: Operation, second_op: Operation) {
             )
     ); "SingleQubitGate")
 ]
+#[test_case(
+    Operation::from(PhaseShiftState0::new(0, CalculatorFloat::from(0))),
+    Operation::from(PhaseShiftState0::new(1, CalculatorFloat::from(0))); "PhaseShiftState0")]
+#[test_case(
+    Operation::from(PhaseShiftState1::new(0, CalculatorFloat::from(0))),
+    Operation::from(PhaseShiftState1::new(1, CalculatorFloat::from(0))); "PhaseShiftState1")]
 fn test_pyo3_richcmp(definition_1: Operation, definition_2: Operation) {
     pyo3::prepare_freethreaded_python();
     let gil = pyo3::Python::acquire_gil();
diff --git a/roqoqo/tests/integration/operations/single_qubit_gate_operations.rs b/roqoqo/tests/integration/operations/single_qubit_gate_operations.rs
index 540ff2d1..b3eebc8d 100644
--- a/roqoqo/tests/integration/operations/single_qubit_gate_operations.rs
+++ b/roqoqo/tests/integration/operations/single_qubit_gate_operations.rs
@@ -391,6 +391,8 @@ fn test_singlequbitgate_debug() {
 #[test_case(SingleQubitGateOperation::from(RotateX::new(0, CalculatorFloat::from(PI/3.0))); "RotateX")]
 #[test_case(SingleQubitGateOperation::from(RotateY::new(0, CalculatorFloat::from(PI/3.0))); "RotateY")]
 #[test_case(SingleQubitGateOperation::from(RotateZ::new(0, CalculatorFloat::from(PI/3.0))); "RotateZ")]
+#[test_case(SingleQubitGateOperation::from(PhaseShiftState0::new(0, CalculatorFloat::from(PI/2.0))); "phaseshiftstate0")]
+#[test_case(SingleQubitGateOperation::from(PhaseShiftState1::new(0, CalculatorFloat::from(PI/2.0))); "phaseshiftstate1")]
 #[test_case(SingleQubitGateOperation::from(PauliX::new(1)); "PauliX")]
 #[test_case(SingleQubitGateOperation::from(PauliY::new(1)); "PauliY")]
 #[test_case( SingleQubitGateOperation::from(PauliZ::new(1)); "PauliZ")]
@@ -456,6 +458,25 @@ fn test_rotatexyz_rotate(qubit: usize, theta: CalculatorFloat) {
     assert_eq!(theta_p, &theta);
 }
 
+/// Test theta() for PhaseShiftState gates
+#[test_case(0, CalculatorFloat::from(0); "test0")]
+#[test_case(1, CalculatorFloat::from("theta"); "test1")]
+fn test_rotatexyz_phaseshiftstate(qubit: usize, theta: CalculatorFloat) {
+    // Test PhaseShiftState0 rotate
+    let gate1 = PhaseShiftState0::new(qubit, theta.clone());
+    let gate2 = PhaseShiftState0::new(qubit, CalculatorFloat::from(gate1.theta().clone()));
+    assert_eq!(gate1, gate2);
+    let theta_p: &CalculatorFloat = gate1.theta();
+    assert_eq!(theta_p, &theta);
+
+    // Test PhaseShiftState1 rotate
+    let gate1 = PhaseShiftState1::new(qubit, theta.clone());
+    let gate2 = PhaseShiftState1::new(qubit, CalculatorFloat::from(gate1.theta().clone()));
+    assert_eq!(gate1, gate2);
+    let theta_p: &CalculatorFloat = gate1.theta();
+    assert_eq!(theta_p, &theta);
+}
+
 /// Test rotate aroundsphericalaxis
 #[test_case(0, CalculatorFloat::from(0), CalculatorFloat::from(0), CalculatorFloat::from(0); "rotate0")]
 #[test_case(
@@ -513,6 +534,8 @@ fn test_rotatearoundsphericalaxis_rotate(
     CalculatorFloat::from("theta"),
     CalculatorFloat::from("spherical_theta"),
     CalculatorFloat::from("spherical_phi"))); "Rotation")]
+#[test_case(0, SingleQubitGateOperation::from(PhaseShiftState0::new(0, CalculatorFloat::from(PI/2.0))); "phaseshiftstate0")]
+#[test_case(1, SingleQubitGateOperation::from(PhaseShiftState1::new(1, CalculatorFloat::from(PI/2.0))); "phaseshiftstate1")]
 fn test_rotatexyz_operatesinglequbit(qubit: usize, gate: SingleQubitGateOperation) {
     let qubit_p: &usize = &gate.qubit();
     assert_eq!(qubit_p, &qubit);
@@ -535,6 +558,8 @@ fn test_rotatexyz_operatesinglequbit(qubit: usize, gate: SingleQubitGateOperatio
     CalculatorFloat::from("theta"),
     CalculatorFloat::from("spherical_theta"),
     CalculatorFloat::from("spherical_phi"))); "Rotation")]
+#[test_case(SingleQubitGateOperation::from(PhaseShiftState0::new(0, CalculatorFloat::from(PI/2.0))); "phaseshiftstate0")]
+#[test_case(SingleQubitGateOperation::from(PhaseShiftState1::new(0, CalculatorFloat::from(PI/2.0))); "phaseshiftstate1")]
 fn test_rotatexyz_clone(gate1: SingleQubitGateOperation) {
     let gate2 = gate1.clone();
     assert_eq!(gate2, gate1);
@@ -571,6 +596,8 @@ fn test_rotatexyz_clone(gate1: SingleQubitGateOperation) {
         CalculatorFloat::from(0.0),
         CalculatorFloat::from(PI),
     )); "SingleQubitGate")]
+#[test_case("PhaseShiftState0", SingleQubitGateOperation::from(PhaseShiftState0::new(0, CalculatorFloat::from(PI/2.0))); "phaseshiftstate0")]
+#[test_case("PhaseShiftState1", SingleQubitGateOperation::from(PhaseShiftState1::new(0, CalculatorFloat::from(PI/2.0))); "phaseshiftstate1")]
 fn test_singlequbitgateoperations_hqslang(name: &'static str, gate: SingleQubitGateOperation) {
     assert!(!gate.hqslang().is_empty());
     assert_eq!(gate.hqslang(), name);
@@ -816,6 +843,8 @@ fn test_singlequbitgates_abp(
     CalculatorFloat::from(0),
     CalculatorFloat::from(0),
     CalculatorFloat::from(0))); "Rotation")]
+#[test_case(SingleQubitGateOperation::from(PhaseShiftState0::new(0, CalculatorFloat::from(PI/2.0))); "phaseshiftstate0")]
+#[test_case(SingleQubitGateOperation::from(PhaseShiftState1::new(0, CalculatorFloat::from(PI/2.0))); "phaseshiftstate1")]
 fn test_is_parametrized_false(gate: SingleQubitGateOperation) {
     let bool_parameter = gate.is_parametrized();
     assert!(!bool_parameter);
@@ -838,6 +867,8 @@ fn test_is_parametrized_false(gate: SingleQubitGateOperation) {
     CalculatorFloat::from(0),
     CalculatorFloat::from(0),
     CalculatorFloat::from(0))); "Rotation")]
+#[test_case(SingleQubitGateOperation::from(PhaseShiftState0::new(0, CalculatorFloat::from(PI/2.0))); "phaseshiftstate0")]
+#[test_case(SingleQubitGateOperation::from(PhaseShiftState1::new(0, CalculatorFloat::from(PI/2.0))); "phaseshiftstate1")]
 fn test_singlequbitgates_unitarity(gate: SingleQubitGateOperation) {
     let result: Result<Array2<Complex64>, RoqoqoError> = gate.unitary_matrix();
     let result_matrix: Array2<Complex64> = result.unwrap();
@@ -888,6 +919,24 @@ fn test_rotatex_substitute_parameters() {
 #[test_case(SingleQubitGateOperation::from(SGate::new(1)); "SGate")]
 #[test_case(SingleQubitGateOperation::from(TGate::new(1)); "TGate")]
 #[test_case(SingleQubitGateOperation::from(Hadamard::new(0)); "Hadamard")]
+#[test_case(SingleQubitGateOperation::from(RotateX::new(0, CalculatorFloat::from(0))); "RotateX")]
+#[test_case(SingleQubitGateOperation::from(RotateY::new(0, CalculatorFloat::from(0))); "RotateY")]
+#[test_case(SingleQubitGateOperation::from(RotateZ::new(0, CalculatorFloat::from(0))); "RotateZ")]
+#[test_case(SingleQubitGateOperation::from(RotateAroundSphericalAxis::new(
+    0,
+    CalculatorFloat::from(0),
+    CalculatorFloat::from(0),
+    CalculatorFloat::from(0))); "Rotation")]
+#[test_case(SingleQubitGateOperation::from(PhaseShiftState0::new(0, CalculatorFloat::from(PI/2.0))); "phaseshiftstate0")]
+#[test_case(SingleQubitGateOperation::from(PhaseShiftState1::new(0, CalculatorFloat::from(PI/2.0))); "phaseshiftstate1")]
+#[test_case(SingleQubitGateOperation::from(SingleQubitGate::new(
+    0,
+    CalculatorFloat::from(1.0),
+    CalculatorFloat::from(0.0),
+    CalculatorFloat::from(0.0),
+    CalculatorFloat::from(0.0),
+    CalculatorFloat::from(0.0),
+)); "singlequbitgate")]
 fn test_ineffective_substitute_parameters(gate: SingleQubitGateOperation) {
     let mut substitution_dict: Calculator = Calculator::new();
     substitution_dict.set_variable("theta", 0.0);
@@ -921,6 +970,32 @@ fn test_rotatez_substitute_parameters() {
     assert_eq!(result.theta().clone(), CalculatorFloat::from(0.0));
 }
 
+/// Test substitute_parameters for PhaseShiftState0
+#[test]
+fn test_phaseshiftstate0_substitute_parameters() {
+    let gate: PhaseShiftState0 = PhaseShiftState0::new(0, CalculatorFloat::from("theta"));
+    assert_eq!(gate.theta().clone(), CalculatorFloat::from("theta"));
+    assert!(gate.is_parametrized());
+    let mut substitution_dict: Calculator = Calculator::new();
+    substitution_dict.set_variable("theta", 0.0);
+    let result = gate.substitute_parameters(&mut substitution_dict).unwrap();
+    assert!(!result.is_parametrized());
+    assert_eq!(result.theta().clone(), CalculatorFloat::from(0.0));
+}
+
+/// Test substitute_parameters for PhaseShiftState1
+#[test]
+fn test_phaseshiftstate1_substitute_parameters() {
+    let gate: PhaseShiftState1 = PhaseShiftState1::new(0, CalculatorFloat::from("theta"));
+    assert_eq!(gate.theta().clone(), CalculatorFloat::from("theta"));
+    assert!(gate.is_parametrized());
+    let mut substitution_dict: Calculator = Calculator::new();
+    substitution_dict.set_variable("theta", 0.0);
+    let result = gate.substitute_parameters(&mut substitution_dict).unwrap();
+    assert!(!result.is_parametrized());
+    assert_eq!(result.theta().clone(), CalculatorFloat::from(0.0));
+}
+
 /// Test substitute parameters for RotateAroundSphericalAxis
 #[test]
 fn test_rotatearoundsphericalaxis_substitute_parameters() {
@@ -983,6 +1058,14 @@ fn test_rotatearoundsphericalaxis_substitute_parameters() {
     SingleQubitGateOperation::from(RotateZ::new(0, CalculatorFloat::from(0))),
     SingleQubitGateOperation::from(RotateZ::new(2, CalculatorFloat::from(0))),
     2; "RotateZ_0-2")]
+#[test_case(
+    SingleQubitGateOperation::from(PhaseShiftState0::new(0, CalculatorFloat::from(0))),
+    SingleQubitGateOperation::from(PhaseShiftState0::new(2, CalculatorFloat::from(0))),
+    2; "PhaseShiftState0")]
+#[test_case(
+    SingleQubitGateOperation::from(PhaseShiftState1::new(0, CalculatorFloat::from(0))),
+    SingleQubitGateOperation::from(PhaseShiftState1::new(2, CalculatorFloat::from(0))),
+    2; "PhaseShiftState1")]
 #[test_case(
     SingleQubitGateOperation::from(RotateZ::new(0, CalculatorFloat::from(0))),
     SingleQubitGateOperation::from(RotateZ::new(0, CalculatorFloat::from(0))),
@@ -1077,9 +1160,12 @@ fn test_singlequbitgates_remap_qubits(
     assert_eq!(result2, Ok(operation.clone()));
 }
 
+/// Test error case of remap_qubits() function for SingleQubitGateOperations
 #[test_case(SingleQubitGateOperation::from(RotateX::new(0, CalculatorFloat::from(0))); "RotateX")]
 #[test_case(SingleQubitGateOperation::from(RotateY::new(0, CalculatorFloat::from(0))); "RotateY")]
 #[test_case(SingleQubitGateOperation::from(RotateZ::new(0, CalculatorFloat::from(0))); "RotateZ")]
+#[test_case(SingleQubitGateOperation::from(PhaseShiftState0::new(0, CalculatorFloat::from(0))); "PhaseShiftState0")]
+#[test_case(SingleQubitGateOperation::from(PhaseShiftState1::new(0, CalculatorFloat::from(0))); "PhaseShiftState1")]
 #[test_case(SingleQubitGateOperation::from(PauliX::new(0)); "PauliX")]
 #[test_case(SingleQubitGateOperation::from(PauliY::new(0)); "PauliY")]
 #[test_case( SingleQubitGateOperation::from(PauliZ::new(0)); "PauliZ")]
@@ -1163,6 +1249,12 @@ fn remap_qubits_error(gate: SingleQubitGateOperation) {
             CalculatorFloat::from(0),
         )
     ); "Rotation")]
+#[test_case(
+    "PhaseShiftState0(PhaseShiftState0 { qubit: 0, theta: Float(0.0) })",
+    SingleQubitGateOperation::from(PhaseShiftState0::new(0, CalculatorFloat::from(0))); "PhaseShiftState0")]
+#[test_case(
+    "PhaseShiftState1(PhaseShiftState1 { qubit: 0, theta: Float(0.0) })",
+    SingleQubitGateOperation::from(PhaseShiftState1::new(0, CalculatorFloat::from(0))); "PhaseShiftState1")]
 fn test_singlequbitgates_debug(name: &'static str, gate: SingleQubitGateOperation) {
     assert_eq!(format!("{:?}", gate), name);
 }
@@ -1180,6 +1272,14 @@ fn test_singlequbitgates_debug(name: &'static str, gate: SingleQubitGateOperatio
     SingleQubitGateOperation::from(RotateZ::new(1, CalculatorFloat::from(1))),
     SingleQubitGateOperation::from(RotateZ::new(0, CalculatorFloat::from(0)));
     "RotateZ")]
+#[test_case(
+    SingleQubitGateOperation::from(PhaseShiftState1::new(1, CalculatorFloat::from(1))),
+    SingleQubitGateOperation::from(PhaseShiftState1::new(0, CalculatorFloat::from(0)));
+    "PhaseShiftState1")]
+#[test_case(
+    SingleQubitGateOperation::from(PhaseShiftState0::new(1, CalculatorFloat::from(1))),
+    SingleQubitGateOperation::from(PhaseShiftState0::new(0, CalculatorFloat::from(0)));
+    "PhaseShiftState0")]
 #[test_case(
     SingleQubitGateOperation::from(PauliX::new(1)),
     SingleQubitGateOperation::from(PauliX::new(0));
@@ -1460,6 +1560,34 @@ fn test_rotatez_powercf(theta: CalculatorFloat, power: CalculatorFloat) {
     assert_eq!(power_gate.global_phase(), test_gate.global_phase());
 }
 
+/// Test powerfc function for PhaseShiftState0 with symbolic parameters
+#[test_case(CalculatorFloat::from("theta"), CalculatorFloat::from("power"); "power_symbolic")]
+fn test_phaseshiftstate0_powercf(theta: CalculatorFloat, power: CalculatorFloat) {
+    let gate = PhaseShiftState0::new(0, theta);
+    let power_gate = gate.powercf(power.clone());
+    let test_theta = power * gate.theta().clone();
+    let test_gate = PhaseShiftState0::new(0, test_theta);
+    assert_eq!(power_gate.alpha_r(), test_gate.alpha_r());
+    assert_eq!(power_gate.alpha_i(), test_gate.alpha_i());
+    assert_eq!(power_gate.beta_r(), test_gate.beta_r());
+    assert_eq!(power_gate.beta_i(), test_gate.beta_i());
+    assert_eq!(power_gate.global_phase(), test_gate.global_phase());
+}
+
+/// Test powerfc function for PhaseShiftState1 with symbolic parameters
+#[test_case(CalculatorFloat::from("theta"), CalculatorFloat::from("power"); "power_symbolic")]
+fn test_phaseshiftstate1_powercf(theta: CalculatorFloat, power: CalculatorFloat) {
+    let gate = PhaseShiftState1::new(0, theta);
+    let power_gate = gate.powercf(power.clone());
+    let test_theta = power * gate.theta().clone();
+    let test_gate = PhaseShiftState1::new(0, test_theta);
+    assert_eq!(power_gate.alpha_r(), test_gate.alpha_r());
+    assert_eq!(power_gate.alpha_i(), test_gate.alpha_i());
+    assert_eq!(power_gate.beta_r(), test_gate.beta_r());
+    assert_eq!(power_gate.beta_i(), test_gate.beta_i());
+    assert_eq!(power_gate.global_phase(), test_gate.global_phase());
+}
+
 /// Test powerfc function for RotateAroundSphericalAxis
 #[test_case(
     0,
@@ -1650,6 +1778,26 @@ fn test_rotatearoundsphericalaxis_powerfc(
         "SingleQubitGate",
         ];
     "SingleQubitGate")]
+#[test_case(
+    SingleQubitGateOperation::from(PhaseShiftState1::new(0, CalculatorFloat::from(0))),
+    vec![
+        "Operation",
+        "GateOperation",
+        "SingleQubitGateOperation",
+        "Rotation",
+        "PhaseShiftState1",
+        ];
+    "PhaseShiftState1")]
+#[test_case(
+    SingleQubitGateOperation::from(PhaseShiftState0::new(0, CalculatorFloat::from(0))),
+    vec![
+        "Operation",
+        "GateOperation",
+        "SingleQubitGateOperation",
+        "Rotation",
+        "PhaseShiftState0",
+        ];
+    "PhaseShiftState0")]
 pub fn test_tags(gate: SingleQubitGateOperation, tags: Vec<&str>) {
     for i in 0..tags.len() {
         assert_eq!(gate.tags()[i], tags[i]);