Пример #1
0
    def expval(self, observable):
        if self.analytic:
            qulacs_observable = Observable(self.num_wires)
            if isinstance(observable.name, list):
                observables = [
                    self._observable_map[obs] for obs in observable.name
                ]
            else:
                observables = [self._observable_map[observable.name]]

            if None not in observables:
                applied_wires = self.map_wires(observable.wires).tolist()
                opp = " ".join([
                    f"{obs} {applied_wires[i]}"
                    for i, obs in enumerate(observables)
                ])

                qulacs_observable.add_operator(1.0, opp)
                return qulacs_observable.get_expectation_value(
                    self._pre_rotated_state)

            # exact expectation value
            eigvals = self._asarray(observable.eigvals, dtype=self.R_DTYPE)
            prob = self.probability(wires=observable.wires)
            return self._dot(eigvals, prob)

        # estimate the ev
        return np.mean(self.sample(observable))
def main():
    import numpy as np
    n_qubit = 2
    obs = Observable(n_qubit)
    initial_state = QuantumState(n_qubit)
    obs.add_operator(1, "Z 0 Z 1")
    circuit_list = []
    p_list = [0.02, 0.04, 0.06, 0.08]

    #prepare circuit list
    for p in p_list:
        circuit = QuantumCircuit(n_qubit)
        circuit.add_H_gate(0)
        circuit.add_RY_gate(1, np.pi / 6)
        circuit.add_CNOT_gate(0, 1)
        circuit.add_gate(
            Probabilistic([p / 4, p / 4, p / 4],
                          [X(0), Y(0), Z(0)]))  #depolarizing noise
        circuit.add_gate(
            Probabilistic([p / 4, p / 4, p / 4],
                          [X(1), Y(1), Z(1)]))  #depolarizing noise
        circuit_list.append(circuit)

    #get mitigated output
    mitigated, non_mitigated_array, fit_coefs = error_mitigation_extrapolate_linear(
        circuit_list,
        p_list,
        initial_state,
        obs,
        n_circuit_sample=100000,
        return_full=True)

    #plot the result
    p = np.linspace(0, max(p_list), 100)
    plt.plot(p,
             fit_coefs[0] * p + fit_coefs[1],
             linestyle="--",
             label="linear fit")
    plt.scatter(p_list, non_mitigated_array, label="un-mitigated")
    plt.scatter(0, mitigated, label="mitigated output")

    #prepare the clean result
    state = QuantumState(n_qubit)
    circuit = QuantumCircuit(n_qubit)
    circuit.add_H_gate(0)
    circuit.add_RY_gate(1, np.pi / 6)
    circuit.add_CNOT_gate(0, 1)
    circuit.update_quantum_state(state)
    plt.scatter(0, obs.get_expectation_value(state), label="True output")
    plt.xlabel("error rate")
    plt.ylabel("expectation value")
    plt.legend()
    plt.show()
Пример #3
0
 def _expectation_value(self, circuit: Circuit, operator: Observable) -> complex:
     state = self._sim(circuit.n_qubits)
     state.set_zero_state()
     ql_circ = tk_to_qulacs(circuit)
     ql_circ.update_quantum_state(state)
     expectation_value = operator.get_expectation_value(state)
     del state
     del ql_circ
     return complex(expectation_value)
Пример #4
0
def convert_openfermion_op(n_qubit, openfermion_op):
    """convert_openfermion_op
    Args:
        n_qubit (:class:`int`)
        openfermion_op (:class:`openfermion.ops.QubitOperator`)
    Returns:
        :class:`qulacs.Observable`
    """
    ret = Observable(n_qubit)

    for pauli_product in openfermion_op.terms:
        coef = float(np.real(openfermion_op.terms[pauli_product]))
        pauli_string = ''
        for pauli_operator in pauli_product:
            pauli_string += pauli_operator[1] + ' ' + str(pauli_operator[0])
            pauli_string += ' '
        ret.add_operator(coef, pauli_string[:-1])

    return ret
Пример #5
0
def qtest(angle):
    state = QuantumState(3)
    state.set_Haar_random_state()
    circuit = QuantumCircuit(3)
    circuit.add_X_gate(0)
    merged_gate = merge(CNOT(0, 1), Y(1))
    circuit.add_gate(merged_gate)
    circuit.add_RX_gate(1, angle)
    circuit.update_quantum_state(state)
    observable = Observable(3)
    observable.add_operator(2.0, "X 2 Y 1 Z 0")
    observable.add_operator(-3.0, "Z 2")
    result = observable.get_expectation_value(state)

    output = {'energy': result}
    return (output)
    def __init__(self, nqubit, c_depth, num_class):
        """
        :param nqubit: qubitの数。必要とする出力の次元数よりも多い必要がある
        :param c_depth: circuitの深さ
        :param num_class: 分類の数(=測定するqubitの数)
        """
        self.nqubit = nqubit
        self.c_depth = c_depth

        self.input_state_list = []  # |ψ_in>のリスト
        self.theta = []  # θのリスト

        self.output_gate = None  # U_out

        self.num_class = num_class  # 分類の数(=測定するqubitの数)

        # オブザーバブルの準備
        obs = [Observable(nqubit) for _ in range(num_class)]
        for i in range(len(obs)):
            obs[i].add_operator(1., f'Z {i}')  # Z0, Z1, Z3をオブザーバブルとして設定
        self.obs = obs
Пример #7
0
    def __init__(self, nqubit, c_depth, num_class):
        """
        :param nqubit: #qubits
        :param c_depth: circuit depth
        :param num_class: # of classification (=# of measured qubits)
        """
        self.nqubit = nqubit
        self.c_depth = c_depth

        self.input_state_list = []  # list of |Psi_in>
        self.theta = []

        self.output_gate = None  # U_out

        self.num_class = num_class  # # of classification (=# of measured qubits)

        # Observable
        obs = [Observable(nqubit) for _ in range(num_class)]
        for i in range(len(obs)):
            obs[i].add_operator(1., 'Z ' + str(i))  # Z0, Z1, Z3
        self.obs = obs
Пример #8
0
    def __init__(self,
                 nqubit,
                 c_depth,
                 num_class,
                 time_step,
                 time_evol_hamiltonian_type='Ising'):
        """
        :param nqubit: #qubits
        :param c_depth: circuit depth
        :param num_class: # of classification (=# of measured qubits)
        :param time_evol_hamiltonian_type: time evolution hamiltonian type; option = 'Ising' or 'Heisenberg'
        """
        self.nqubit = nqubit
        self.c_depth = c_depth

        self.input_state_list = []  # list of |Psi_in>
        self.theta = []

        self.output_gate = None  # U_out

        self.num_class = num_class  # of classification (=# of measured qubits)
        self.time_step = time_step

        self.time_evol_hamiltonian_type = time_evol_hamiltonian_type
        try:
            if self.time_evol_hamiltonian_type == 'Ising' or self.time_evol_hamiltonian_type == 'Heisenberg':
                pass
            else:
                raise NameError
        except NameError:
            print('Input the correct time evolution hamiltonian type')

        # Observable
        obs = [Observable(nqubit) for _ in range(num_class)]
        for i in range(len(obs)):
            obs[i].add_operator(1., 'Z ' + str(i))  # Z0, Z1, Z3
        self.obs = obs
Пример #9
0
def test_VqeOptimizer():
    from qulacs import ParametricQuantumCircuit
    from qulacs import QuantumState
    from qulacs import Observable
    from qulacs.gate import Probabilistic, X, Y, Z
    import numpy as np
    import matplotlib.pyplot as plt

    n_qubit = 2
    p_list = [0.05, 0.1, 0.15]
    parametric_circuit_list = \
        [ParametricQuantumCircuit(n_qubit)
         for i in range(len(p_list))]
    initial_state = QuantumState(n_qubit)

    for (p, circuit) in zip(p_list, parametric_circuit_list):
        circuit.add_H_gate(0)
        circuit.add_parametric_RY_gate(1, np.pi / 6)
        circuit.add_CNOT_gate(0, 1)
        prob = Probabilistic([p / 4, p / 4, p / 4], [X(0), Y(0), Z(0)])
        circuit.add_gate(prob)

    noiseless_circuit = ParametricQuantumCircuit(n_qubit)
    noiseless_circuit.add_H_gate(0)
    noiseless_circuit.add_parametric_RY_gate(1, np.pi / 6)
    noiseless_circuit.add_CNOT_gate(0, 1)

    n_sample_per_circuit = 1
    n_circuit_sample = 1000
    obs = Observable(n_qubit)
    obs.add_operator(1.0, "Z 0 Z 1")
    obs.add_operator(0.5, "X 0 X 1")
    initial_param = np.array([np.pi / 6])

    opt = VqeOptimizer(parametric_circuit_list,
                       initial_state,
                       obs,
                       initial_param,
                       p_list,
                       n_circuit_sample=n_circuit_sample,
                       n_sample_per_circuit=n_sample_per_circuit,
                       noiseless_circuit=noiseless_circuit)

    noisy = opt.sample_output(initial_param)
    mitigated, exp_array, _ = opt.sample_mitigated_output(initial_param,
                                                          return_full=True)
    exact = opt.exact_output(initial_param)

    print(noisy, exact)
    print(exp_array, mitigated)

    opt_param = opt.optimize()
    print(opt_param)
    theta_list = np.linspace(0, np.pi, 100)
    output_list = [opt.exact_output([theta]) for theta in theta_list]
    plt.plot(theta_list,
             output_list,
             color="black",
             linestyle="dashed",
             label="exact")
    plt.scatter(opt.parameter_history,
                opt.exp_history,
                c="blue",
                label="optimization history")
    plt.xlabel("theta")
    plt.ylabel("output")
    plt.legend()
    plt.show()
Пример #10
0
 def test_observable(self):
     from qulacs import Observable
     obs = Observable(1)
     obs.add_operator(1.0, "X 0")
     term = obs.get_term(0)
     del term
Пример #11
0
        U.add_RY_gate(i, angle_y)
        U.add_RZ_gate(i, angle_z)

    return U

# Function to update theta
def set_U_out(theta):
    global U_out

    parameter_count = U_out.get_parameter_count()

    for i in range(parameter_count):
        U_out.set_parameter(i, theta[i])

# Construct an observable gate
obs = Observable(nqubit)
obs.add_operator(1, "Z 0")
obs.add_operator(2, "Z 1")
#obs.add_operator(4, "Z 2")

# Function for prediction
def qcl_pred(x, U_out):

    # Output state
    U_out.update_quantum_state(x)

    # Output from the model
    res = obs.get_expectation_value(state)

    return res
Пример #12
0
"""
probabilistic bit flip noise
"""

from qulacs import Observable
from qulacs import QuantumState, QuantumCircuit
from qulacs.gate import Probabilistic, X

import matplotlib.pyplot as plt

obs = Observable(1)
obs.add_operator(1, "Z 0")
state = QuantumState(1)
circuit = QuantumCircuit(1)
p = 0.1  # probability of bit flip
n_circuit_sample = 10000
n_depth = 20  # the number of probabilistic gate

probabilistic_pauli_gate = Probabilistic([p],
                                         [X(0)])  #define probabilistic gate

circuit.add_gate(probabilistic_pauli_gate)  # add the prob. gate to the circuit

exp_array = []
for depth in range(n_depth):
    exp = 0
    for i in [0] * n_circuit_sample:
        state.set_zero_state()
        for _ in range(depth):
            circuit.update_quantum_state(state)  # apply the prob. gate
        exp += obs.get_expectation_value(
Пример #13
0
#circuit.add_H_gate(1)
#circuit.add_H_gate(2)
circuit.add_RX_gate(0, 0.1)
circuit.add_RX_gate(1, 0.1)
#circuit.add_RX_gate(2, 0.1)
merged_gate = merge(CNOT(0,1),Y(1))
circuit.add_gate(merged_gate)
meas0 = Measurement(0, 0)
circuit.add_gate(meas0)
meas1 = Measurement(1, 1)
circuit.add_gate(meas1)
#meas2 = Measurement(2, 2)
#circuit.add_gate(meas2)
print(circuit)

observable = Observable(nqubit)
observable.add_operator(1, "Z 0")
observable.add_operator(2, "Z 1")
#observable.add_operator(4, "Z 2")

data = list()
x_value = list()
y_value = list()

for i in range(n_data):
    #state.set_Haar_random_state()
    x = random.random()
    state.set_zero_state() # U_in|000>
    U_in(x).update_quantum_state(state)
    state_vec = state.get_vector()
    circuit.update_quantum_state(state)
# Take the initial theta
parameter_count = U_out.get_parameter_count()
theta_init = [U_out.get_parameter(ind) for ind in range(parameter_count)]

# Function to update theta
def set_U_out(theta):
    global U_out

    parameter_count = U_out.get_parameter_count()

    for i in range(parameter_count):
        U_out.set_parameter(i, theta[i])

# Construct an observable gate
from qulacs import Observable
obs = Observable(nqubit)
obs.add_operator(2.,'Z 0') # Add an operator 2*Z. This number should be optimised.

# Function for prediction
def qcl_pred(x, U_out):
    state = QuantumState(nqubit)
    state.set_zero_state()

    # Input state
    U_in(x).update_quantum_state(state)

    # Output state
    U_out.update_quantum_state(state)

    # Output from the model
    res = obs.get_expectation_value(state)