Merge pull request #4 from mattia-robbiano/fixes

Fixes
This commit is contained in:
Mattia Robbiano
2025-10-01 18:31:19 +02:00
committed by GitHub

View File

@@ -1,4 +1,5 @@
from collections import Counter from collections import Counter
from typing import Optional
import quimb as qu import quimb as qu
import quimb.tensor as qtn import quimb.tensor as qtn
@@ -46,6 +47,11 @@ if not __name__ == "__main__":
self.platform = "quimb" self.platform = "quimb"
self.backend = quimb_backend self.backend = quimb_backend
self.ansatz = None
self.max_bond_dimension = None
self.svd_cutoff = None
self.n_most_frequent_states = None
self.configure_tn_simulation() self.configure_tn_simulation()
self.setup_backend_specifics( self.setup_backend_specifics(
quimb_backend=quimb_backend, contractions_optimizer=contraction_optimizer quimb_backend=quimb_backend, contractions_optimizer=contraction_optimizer
@@ -53,8 +59,9 @@ if not __name__ == "__main__":
def configure_tn_simulation( def configure_tn_simulation(
self, self,
ansatz: str = None, ansatz: str = "mps",
max_bond_dimension: int = 10, max_bond_dimension: Optional[int] = None,
svd_cutoff: Optional[float] = 1e-10,
n_most_frequent_states: int = 100, n_most_frequent_states: int = 100,
): ):
""" """
@@ -73,8 +80,15 @@ if not __name__ == "__main__":
""" """
self.ansatz = ansatz self.ansatz = ansatz
self.max_bond_dimension = max_bond_dimension self.max_bond_dimension = max_bond_dimension
self.svd_cutoff = svd_cutoff
self.n_most_frequent_states = n_most_frequent_states self.n_most_frequent_states = n_most_frequent_states
@property
def circuit_ansatz(self):
if self.ansatz == "mps":
return qtn.CircuitMPS
return qtn.Circuit
def setup_backend_specifics( def setup_backend_specifics(
self, quimb_backend="numpy", contractions_optimizer="auto-hq" self, quimb_backend="numpy", contractions_optimizer="auto-hq"
): ):
@@ -152,10 +166,7 @@ if not __name__ == "__main__":
ValueError, "Initial state not None supported only for MPS ansatz." ValueError, "Initial state not None supported only for MPS ansatz."
) )
circ_ansatz = ( circ_quimb = self.circuit_ansatz.from_openqasm2_str(
qtn.circuit.CircuitMPS if self.ansatz == "MPS" else qtn.circuit.Circuit
)
circ_quimb = circ_ansatz.from_openqasm2_str(
circuit.to_qasm(), psi0=initial_state circuit.to_qasm(), psi0=initial_state
) )
@@ -219,8 +230,8 @@ if not __name__ == "__main__":
""" """
quimb_circuit = self._qibo_circuit_to_quimb( quimb_circuit = self._qibo_circuit_to_quimb(
circuit, circuit,
quimb_circuit_type=qtn.CircuitMPS if self.ansatz == "MPS" else qtn.Circuit, quimb_circuit_type=self.circuit_ansatz,
gate_opts={"max_bond": self.max_bond_dimension}, gate_opts={"max_bond": self.max_bond_dimension, "cutoff": self.svd_cutoff},
) )
expectation_value = 0.0 expectation_value = 0.0
@@ -303,7 +314,6 @@ if not __name__ == "__main__":
The corresponding Quimb operator. The corresponding Quimb operator.
""" """
op_str = op_str.lower() op_str = op_str.lower()
# breakpoint()
op = qu.pauli(op_str[0]) op = qu.pauli(op_str[0])
for c in op_str[1:]: for c in op_str[1:]:
op = op & qu.pauli(c) op = op & qu.pauli(c)
@@ -322,6 +332,7 @@ def QuimbBackend(
"expectation_observable_symbolic_from_state": expectation_observable_symbolic_from_state, "expectation_observable_symbolic_from_state": expectation_observable_symbolic_from_state,
"_qibo_circuit_to_quimb": _qibo_circuit_to_quimb, "_qibo_circuit_to_quimb": _qibo_circuit_to_quimb,
"_string_to_quimb_operator": _string_to_quimb_operator, "_string_to_quimb_operator": _string_to_quimb_operator,
"circuit_ansatz": circuit_ansatz,
} }
if quimb_backend == "numpy": if quimb_backend == "numpy":
from qibo.backends import NumpyBackend from qibo.backends import NumpyBackend