def suspend_test_phase_estimation_debug(self): theta = 5*np.pi/16 n_qubits = 2 a_idx = 1 k = 2 circuit = QuantumCircuit(n_qubits) psi = QuantumState(n_qubits) # |ancilla>|logical> phi = 1.25/2 print('k={}, phi={} mod (np.pi)'.format(k, phi)) # Apply H to ancilla bit to get |+> state circuit.add_H_gate(a_idx) # Apply kickback phase rotation to ancilla bit circuit.add_RZ_gate(a_idx, -np.pi * phi) # Apply C-U(Z0) theta_k = 2 ** (k-1) * theta print('phase:{} mod (np.pi)'.format(theta_k/np.pi)) circuit.add_RZ_gate(0, -theta_k) circuit.add_CNOT_gate(a_idx, 0) circuit.add_RZ_gate(0, theta_k) circuit.add_CNOT_gate(a_idx, 0) # Apply H to ancilla bit to get |+> state circuit.add_H_gate(a_idx) # run circuit circuit.update_quantum_state(psi) print(psi.get_vector()) # partial trace p0 = psi.get_marginal_probability([2, 0]) p1 = psi.get_marginal_probability([2, 1]) print(p0, p1)
def create_input_gate(self, x, uin_type): # Encode x into quantum state # x = 2-dim. variables, [-1,1] u = QuantumCircuit(self.nqubit) angle_y = np.arcsin(x) angle_z = np.arccos(x**2) if uin_type == 0: for i in range(self.nqubit): u.add_RY_gate(i, angle_y[i]) u.add_RZ_gate(i, angle_z[i]) elif uin_type == 1: #for d in range(2): for i in range(self.nqubit): u.add_H_gate(i) u.add_RY_gate(i, angle_y[i]) u.add_RZ_gate(i, angle_z[i]) # KT: add second order expansion for i in range(self.nqubit - 1): for j in range(i + 1, self.nqubit): angle_z2 = np.arccos(x[i] * x[j]) u.add_CNOT_gate(i, j) u.add_RZ_gate(j, angle_z2) u.add_CNOT_gate(i, j) return u
def set_circuit_bcs(ansatz, n_qubits, n_orbitals, ndim1, ndim, theta_list, k): circuit = QuantumCircuit(n_qubits) target_list = np.empty(2) pauli_index = np.empty(2) for i in range(k): ioff = i * ndim for p in range(n_orbitals): pa = 2 * p pb = 2 * p + 1 target_list = pa, pb pauli_index = 1, 2 gate = PauliRotation(target_list, pauli_index, -theta_list[p + ioff]) circuit.add_gate(gate) pauli_index = 2, 1 gate = PauliRotation(target_list, pauli_index, -theta_list[p + ioff]) circuit.add_gate(gate) if "ebcs" in ansatz: if p < n_orbitals - 1: circuit.add_CNOT_gate(pa, pa + 2) circuit.add_CNOT_gate(pb, pb + 2) upcc_Gsingles(circuit, n_orbitals, theta_list, ndim1, n_orbitals, i) return circuit
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()
def ansatz_circuit(n_qubit, depth, theta_list): circuit = QuantumCircuit(n_qubit) for i in range(n_qubit): circuit.add_gate(RY(i, theta_list[i])) for d in range(depth): for i in range(1, n_qubit): circuit.add_H_gate(i) for j in range(n_qubit - 1): circuit.add_CNOT_gate(j, j + 1) circuit.add_gate(RY(j, theta_list[n_qubit * (1 + d) + j])) circuit.add_H_gate(j + 1) circuit.add_gate( RY(n_qubit - 1, theta_list[n_qubit * (1 + d) + n_qubit - 1])) return circuit
def ctrl_RZ_circuit(theta_k, kickback_phase): n_qubits = 2 a_idx = 1 phi = kickback_phase / 2 circuit = QuantumCircuit(n_qubits) # Apply H to ancilla bit to get |+> state circuit.add_H_gate(a_idx) # Apply kickback phase rotation to ancilla bit circuit.add_RZ_gate(a_idx, -np.pi * phi) # Apply C-U(Z0) # print('phase:{} mod (np.pi)'.format(theta_k/np.pi)) circuit.add_RZ_gate(0, -theta_k) circuit.add_CNOT_gate(a_idx, 0) circuit.add_RZ_gate(0, theta_k) circuit.add_CNOT_gate(a_idx, 0) # Apply H to ancilla bit to get |+> state circuit.add_H_gate(a_idx) return circuit
def test_CU_Z0(self): n_qubits = 2 a_idx = 1 theta = np.pi/8 state = QuantumState(n_qubits) input_states_bin = [0b00, 0b10] input_states = [] output_states = [] circuit_H = QuantumCircuit(n_qubits) circuit_H.add_H_gate(0) # |0>|+> and |1>|+> for b in input_states_bin: psi = state.copy() psi.set_computational_basis(b) input_states += [psi] circuit_H.update_quantum_state(psi) circuit = QuantumCircuit(n_qubits) circuit.add_RZ_gate(0, -0.5*theta) circuit.add_CNOT_gate(a_idx, 0) circuit.add_RZ_gate(0, 0.5*theta) circuit.add_CNOT_gate(a_idx, 0) for in_state in input_states: psi = in_state.copy() circuit.update_quantum_state(psi) output_states += [psi] p_list = [] for in_state in input_states: for out_state in output_states: p_list += [inner_product(in_state, out_state)] # <0|<+|0>|+> = 1 # <0|<+|1>|H> = 0 # <1|<+|0>|+> = 0 # <1|<+|1>|H> = cos(pi/16) exp_list = [1.0, 0.0, 0.0, np.cos(theta/2)] for result, expected in zip(p_list, exp_list): self.assertAlmostEqual(result, expected, places=6)
def test_CU_Y0Y1(self): n_qubits = 3 a_idx = 2 theta = np.pi/4 state = QuantumState(n_qubits) input_states_bin = [0b001, 0b010, 0b101, 0b110] input_states = [] output_states = [] circuit = QuantumCircuit(n_qubits) # change basis from Z to Y circuit.add_S_gate(0) circuit.add_S_gate(1) circuit.add_H_gate(0) circuit.add_H_gate(1) circuit.add_CNOT_gate(1, 0) # RZ circuit.add_RZ_gate(0, -0.5*theta) circuit.add_CNOT_gate(a_idx, 0) circuit.add_RZ_gate(0, 0.5*theta) circuit.add_CNOT_gate(a_idx, 0) circuit.add_CNOT_gate(1, 0) # change basis from Z to Y circuit.add_H_gate(0) circuit.add_H_gate(1) circuit.add_Sdag_gate(0) circuit.add_Sdag_gate(1) for b in input_states_bin: psi = state.copy() psi.set_computational_basis(b) input_states += [psi] psi_out = psi.copy() circuit.update_quantum_state(psi_out) output_states += [psi_out] p_list = [] for in_state in input_states: for out_state in output_states: prod = inner_product(in_state, out_state) p_list += [prod] # |001> exp_list = [1.0, 0.0, 0.0, 0.0] # |010> exp_list += [0.0, 1.0, 0.0, 0.0] # |101> exp_list += [0.0, 0.0, np.cos(theta/2), complex(0, -np.sin(theta/2))] # |110> exp_list += [0.0, 0.0, complex(0, -np.sin(theta/2)), np.cos(theta/2)] for result, expected in zip(p_list, exp_list): self.assertAlmostEqual(result, expected, places=6)
def test_iterative_phase_estimation(self): theta = 5*np.pi/16 # theta = np.pi/3 # -0.5235987755982988 # print(-theta/2) n_itter = 6 n_qubits = 2 a_idx = 1 state = QuantumState(n_qubits) # |ancilla>|logical> kickback_phase = 0.0 for k in reversed(range(1, n_itter)): psi = state.copy() phi = kickback_phase/2 # print('k={}, phi={} mod (np.pi)'.format(k, phi)) circuit = QuantumCircuit(n_qubits) # Apply H to ancilla bit to get |+> state circuit.add_H_gate(a_idx) # Apply kickback phase rotation to ancilla bit circuit.add_RZ_gate(a_idx, -np.pi * phi) # Apply C-U(Z0) theta_k = 2 ** (k-1) * theta # print('phase:{} mod (np.pi)'.format(theta_k/np.pi)) circuit.add_RZ_gate(0, -theta_k) circuit.add_CNOT_gate(a_idx, 0) circuit.add_RZ_gate(0, theta_k) circuit.add_CNOT_gate(a_idx, 0) # Apply H to ancilla bit to get |+> state circuit.add_H_gate(a_idx) # run circuit circuit.update_quantum_state(psi) # print(psi.get_vector()) # partial trace p0 = psi.get_marginal_probability([2, 0]) p1 = psi.get_marginal_probability([2, 1]) # print(p0, p1) # update kickback phase kth_digit = 1 if (p0 < p1) else 0 kickback_phase = kickback_phase/2 + kth_digit # print(kickback_phase) # print(-np.pi * kickback_phase/2) self.assertAlmostEqual(-np.pi * kickback_phase/2, -theta/2)
def _try_append_gate(self, op: ops.GateOperation, qulacs_circuit: qulacs.QuantumCircuit, indices: np.array): # One qubit gate if isinstance(op.gate, ops.pauli_gates._PauliX): qulacs_circuit.add_X_gate(indices[0]) elif isinstance(op.gate, ops.pauli_gates._PauliY): qulacs_circuit.add_Y_gate(indices[0]) elif isinstance(op.gate, ops.pauli_gates._PauliZ): qulacs_circuit.add_Z_gate(indices[0]) elif isinstance(op.gate, ops.common_gates.HPowGate): qulacs_circuit.add_H_gate(indices[0]) elif isinstance(op.gate, ops.common_gates.XPowGate): qulacs_circuit.add_RX_gate(indices[0], -np.pi * op.gate._exponent) elif isinstance(op.gate, ops.common_gates.YPowGate): qulacs_circuit.add_RY_gate(indices[0], -np.pi * op.gate._exponent) elif isinstance(op.gate, ops.common_gates.ZPowGate): qulacs_circuit.add_RZ_gate(indices[0], -np.pi * op.gate._exponent) elif isinstance(op.gate, ops.SingleQubitMatrixGate): mat = op.gate._matrix qulacs_circuit.add_dense_matrix_gate(indices[0], mat) elif isinstance(op.gate, circuits.qasm_output.QasmUGate): lmda = op.gate.lmda theta = op.gate.theta phi = op.gate.phi gate = qulacs.gate.U3(indices[0], theta * np.pi, phi * np.pi, lmda * np.pi) qulacs_circuit.add_gate(gate) # Two qubit gate elif isinstance(op.gate, ops.common_gates.CNotPowGate): if op.gate._exponent == 1.0: qulacs_circuit.add_CNOT_gate(indices[0], indices[1]) else: mat = _get_google_rotx(op.gate._exponent) gate = qulacs.gate.DenseMatrix(indices[1], mat) gate.add_control_qubit(indices[0], 1) qulacs_circuit.add_gate(gate) elif isinstance(op.gate, ops.common_gates.CZPowGate): if op.gate._exponent == 1.0: qulacs_circuit.add_CZ_gate(indices[0], indices[1]) else: mat = _get_google_rotz(op.gate._exponent) gate = qulacs.gate.DenseMatrix(indices[1], mat) gate.add_control_qubit(indices[0], 1) qulacs_circuit.add_gate(gate) elif isinstance(op.gate, ops.common_gates.SwapPowGate): if op.gate._exponent == 1.0: qulacs_circuit.add_SWAP_gate(indices[0], indices[1]) else: qulacs_circuit.add_dense_matrix_gate(indices, op._unitary_()) elif isinstance(op.gate, ops.parity_gates.XXPowGate): qulacs_circuit.add_multi_Pauli_rotation_gate( indices, [1, 1], -np.pi * op.gate._exponent) elif isinstance(op.gate, ops.parity_gates.YYPowGate): qulacs_circuit.add_multi_Pauli_rotation_gate( indices, [2, 2], -np.pi * op.gate._exponent) elif isinstance(op.gate, ops.parity_gates.ZZPowGate): qulacs_circuit.add_multi_Pauli_rotation_gate( indices, [3, 3], -np.pi * op.gate._exponent) elif isinstance(op.gate, ops.TwoQubitMatrixGate): indices.reverse() mat = op.gate._matrix qulacs_circuit.add_dense_matrix_gate(indices, mat) # Three qubit gate """ # deprecated because these functions cause errors in gpu elif isinstance(op.gate, ops.three_qubit_gates.CCXPowGate): mat = _get_google_rotx(op.gate._exponent) gate = qulacs.gate.DenseMatrix(indices[2], mat) gate.add_control_qubit(indices[0],1) gate.add_control_qubit(indices[1],1) qulacs_circuit.add_gate(gate) elif isinstance(op.gate, ops.three_qubit_gates.CCZPowGate): mat = _get_google_rotz(op.gate._exponent) gate = qulacs.gate.DenseMatrix(indices[2], mat) gate.add_control_qubit(indices[0],1) gate.add_control_qubit(indices[1],1) qulacs_circuit.add_gate(gate) """ elif isinstance(op.gate, ops.three_qubit_gates.CSwapGate): mat = np.zeros(shape=(4, 4)) mat[0, 0] = 1 mat[1, 2] = 1 mat[2, 1] = 1 mat[3, 3] = 1 gate = qulacs.gate.DenseMatrix(indices[1:], mat) gate.add_control_qubit(indices[0], 1) qulacs_circuit.add_gate(gate) # Misc elif protocols.has_unitary(op): indices.reverse() mat = op._unitary_() qulacs_circuit.add_dense_matrix_gate(indices, mat) # Not unitary else: return False return True
def time_evolution_circuit_improved(g_list, t, kickback_phase, k, n_trotter_step=1): n_qubits = 3 a_idx = 2 phi = -(t / n_trotter_step) * g_list # print(phi) circuit = QuantumCircuit(n_qubits) circuit.add_H_gate(a_idx) # Apply kickback phase rotation to ancilla bit circuit.add_RZ_gate(a_idx, -np.pi * kickback_phase / 2) for _ in range(n_trotter_step): for _ in range(2**k): # CU(Z0) circuit.add_RZ_gate(0, -phi[0]) circuit.add_CNOT_gate(a_idx, 0) circuit.add_RZ_gate(0, phi[0]) circuit.add_CNOT_gate(a_idx, 0) # CU(Y0 Y1) circuit.add_S_gate(0) circuit.add_S_gate(1) circuit.add_H_gate(0) circuit.add_H_gate(1) circuit.add_CNOT_gate(1, 0) circuit.add_RZ_gate(0, -phi[1]) circuit.add_CNOT_gate(a_idx, 0) circuit.add_RZ_gate(0, phi[1]) circuit.add_CNOT_gate(a_idx, 0) circuit.add_CNOT_gate(1, 0) circuit.add_H_gate(0) circuit.add_H_gate(1) circuit.add_Sdag_gate(0) circuit.add_Sdag_gate(1) # CU(Z1) circuit.add_RZ_gate(1, -phi[2]) circuit.add_CNOT_gate(a_idx, 1) circuit.add_RZ_gate(1, phi[2]) circuit.add_CNOT_gate(a_idx, 1) # CU(X0 X1) circuit.add_H_gate(0) circuit.add_H_gate(1) circuit.add_CNOT_gate(1, 0) circuit.add_RZ_gate(0, -phi[3]) circuit.add_CNOT_gate(a_idx, 0) circuit.add_RZ_gate(0, phi[3]) circuit.add_CNOT_gate(a_idx, 0) circuit.add_CNOT_gate(1, 0) circuit.add_H_gate(0) circuit.add_H_gate(1) circuit.add_H_gate(a_idx) return circuit
def main(): ## Example1 circuit = QuantumCircuit(3) circuit.add_X_gate(0) circuit.add_Y_gate(1) circuit.add_Z_gate(2) circuit.add_dense_matrix_gate([0,1], [[1,0,0,0],[0,1,0,0],[0,0,0,1],[0,0,1,0]]) circuit.add_CNOT_gate(2,0) circuit.add_X_gate(2) draw_circuit(circuit, verbose=1) ## Example2 circuit = QuantumCircuit(3) circuit.add_X_gate(0) circuit.add_Y_gate(1) circuit.add_dense_matrix_gate([0,1], [[1,0,0,0],[0,1,0,0],[0,0,0,1],[0,0,1,0]]) circuit.add_Z_gate(2) circuit.add_CNOT_gate(2,0) circuit.add_X_gate(2) draw_circuit(circuit, verbose=1) ## Example3 circuit = QuantumCircuit(3) circuit.add_X_gate(1) circuit.add_CZ_gate(0,2) circuit.add_X_gate(1) draw_circuit(circuit) ## Example4 circuit = QuantumCircuit(4) ##CCX0,2, 3 cx_gate = CNOT(2,3) cx_mat_gate = to_matrix_gate(cx_gate) control_index = 0 control_with_value = 1 cx_mat_gate.add_control_qubit(control_index, control_with_value) circuit.add_gate(cx_mat_gate) ##CCX1,2, 3 ccx = TOFFOLI(1,2, 3) circuit.add_gate(ccx) ##CCX1,2, 0 ccx = TOFFOLI(1,2, 0) circuit.add_gate(ccx) ##CCX1,3, 0 ccx = TOFFOLI(1,3, 0) circuit.add_gate(ccx) ##CCX1,3, 2 ccx = TOFFOLI(1,3, 2) circuit.add_gate(ccx) ##SWAP0,1 circuit.add_SWAP_gate(0,1) ##SWAP0,2 circuit.add_SWAP_gate(0,2) ##SWAP1,3 circuit.add_SWAP_gate(1,3) draw_circuit(circuit, verbose=1) ## Example5 circuit = QuantumCircuit(5) ## 3-qubit gate applied to [0,1,2] mat = np.identity(2**3) circuit.add_dense_matrix_gate([0,1,2], mat) ## 3-qubit gate applied to [0,3,4], and [1] qubit is control-qubit c_dense_gate = DenseMatrix([0,3,4], mat) control_index = 1 control_with_value = 1 c_dense_gate.add_control_qubit(control_index, control_with_value) circuit.add_gate(c_dense_gate) ## 3-qubit gate applied to [0,2,4] circuit.add_dense_matrix_gate([0,2,4], mat) ## SWAP gate aplied to [1,3], and [2] qubit is control-qubit swp_gate = to_matrix_gate(SWAP(1,3)) control_index = 2 control_with_value = 1 swp_gate.add_control_qubit(control_index, control_with_value) circuit.add_gate(swp_gate) draw_circuit(circuit)
def create_input_gate(self, x, uin_type): # Encode x into quantum state # uin_type: unitary data-input type 0, 1, 20, 21, 30, 31, 40, 41, 50, 51, 60, 61 # x = 1dim. variables, [-1,1] I_mat = np.eye(2, dtype=complex) X_mat = X(0).get_matrix() Y_mat = Y(0).get_matrix() Z_mat = Z(0).get_matrix() #make operators s.t. exp(i*theta * sigma^z_j@sigma^z_k) @:tensor product def ZZ(u, theta, j, k): u.add_CNOT_gate(j, k) u.add_RZ_gate(k, -2 * theta * self.time_step) u.add_CNOT_gate(j, k) return u def XX(u, theta, j, k): u.add_H_gate(j) u.add_H_gate(k) ZZ(u, theta, j, k) u.add_H_gate(j) u.add_H_gate(k) return u def YY(u, theta, j, k): u.add_U1_gate(j, -np.pi / 2.) u.add_U1_gate(k, -np.pi / 2.) XX(u, theta, j, k) u.add_U1_gate(j, np.pi / 2.) u.add_U1_gate(k, np.pi / 2.) return u theta = x u = QuantumCircuit(self.nqubit) angle_y = np.arcsin(x) angle_z = np.arccos(x**2) if uin_type == 0: for i in range(self.nqubit): u.add_RY_gate(i, angle_y[i]) u.add_RZ_gate(i, angle_z[i]) elif uin_type == 1: #for d in range(2): for i in range(self.nqubit): u.add_H_gate(i) u.add_RY_gate(i, angle_y[i]) u.add_RZ_gate(i, angle_z[i]) # KT: add second order expansion for i in range(self.nqubit - 1): for j in range(i + 1, self.nqubit): angle_z2 = np.arccos(x[i] * x[j]) u.add_CNOT_gate(i, j) u.add_RZ_gate(j, angle_z2) u.add_CNOT_gate(i, j) elif uin_type == 20: for i in range(self.nqubit): u.add_RX_gate(i, -2 * x[i] * self.time_step) elif uin_type == 21: ham = np.zeros((2**self.nqubit, 2**self.nqubit), dtype=complex) for i in range(self.nqubit): # i runs 0 to nqubit-1 J_x = x[i] print(x) ham += J_x * make_fullgate([[i, X_mat]], self.nqubit) ## Build time-evolution operator by diagonalizing the Ising hamiltonian H*P = P*D <-> H = P*D*P^dagger diag, eigen_vecs = np.linalg.eigh(ham) time_evol_op = np.dot( np.dot(eigen_vecs, np.diag(np.exp(-1j * self.time_step * diag))), eigen_vecs.T.conj()) # e^-iHT # Convert to qulacs gate time_evol_gate = DenseMatrix([i for i in range(self.nqubit)], time_evol_op) u.add_gate(time_evol_gate) elif uin_type == 30: #Ising hamiltonian with input coefficient # nearest neighbor spin-conbination has interaction for i in range(self.nqubit): u.add_RX_gate(i, -2 * x[i] * self.time_step) ZZ(u, theta[i] * theta[(i + 1) % self.nqubit], i, i + 1) elif uin_type == 31: ham = np.zeros((2**self.nqubit, 2**self.nqubit), dtype=complex) for i in range(self.nqubit): J_x = x[i] ham += J_x * make_fullgate([[i, X_mat]], self.nqubit) J_zz = x[i] * x[(i + 1) % self.nqubit] ham += J_zz * make_fullgate( [[i, Z_mat], [(i + 1) % self.nqubit, Z_mat]], self.nqubit) diag, eigen_vecs = np.linalg.eigh(ham) time_evol_op = np.dot( np.dot(eigen_vecs, np.diag(np.exp(-1j * self.time_step * diag))), eigen_vecs.T.conj()) time_evol_gate = DenseMatrix([i for i in range(self.nqubit)], time_evol_op) u.add_gate(time_evol_gate) elif uin_type == 40: #Ising hamiltonian with input coefficient # every two possible spin-conbination has interaction for i in range(self.nqubit): u.add_RX_gate(i, -2 * x[i] * self.time_step) for j in range(i + 1, self.nqubit): ZZ(u, theta[i] * theta[j], i, j) elif uin_type == 41: ham = np.zeros((2**self.nqubit, 2**self.nqubit), dtype=complex) for i in range(self.nqubit): J_x = x[i] ham += J_x * make_fullgate([[i, X_mat]], self.nqubit) for j in range(i + 1, self.nqubit): J_ij = x[i] * x[j] ham += J_ij * make_fullgate([[i, Z_mat], [j, Z_mat]], self.nqubit) diag, eigen_vecs = np.linalg.eigh(ham) time_evol_op = np.dot( np.dot(eigen_vecs, np.diag(np.exp(-1j * self.time_step * diag))), eigen_vecs.T.conj()) time_evol_gate = DenseMatrix([i for i in range(self.nqubit)], time_evol_op) u.add_gate(time_evol_gate) elif uin_type == 50: #Heisenberg hamiltonian with input coefficient # nearest neighbor spin-conbination has interaction for i in range(self.nqubit): u.add_RX_gate(i, -2 * x[i] * self.time_step) XX(u, theta[i] * theta[(i + 1) % self.nqubit], i, i + 1) YY(u, theta[i] * theta[(i + 1) % self.nqubit], i, i + 1) ZZ(u, theta[i] * theta[(i + 1) % self.nqubit], i, i + 1) elif uin_type == 51: ham = np.zeros((2**self.nqubit, 2**self.nqubit), dtype=complex) for i in range(self.nqubit): J_x = x[i] ham += J_x * make_fullgate([[i, X_mat]], self.nqubit) J_xx = x[i] * x[(i + 1) % self.nqubit] J_yy = x[i] * x[(i + 1) % self.nqubit] J_zz = x[i] * x[(i + 1) % self.nqubit] ham += J_xx * make_fullgate( [[i, X_mat], [(i + 1) % self.nqubit, X_mat]], self.nqubit) ham += J_yy * make_fullgate( [[i, Y_mat], [(i + 1) % self.nqubit, Y_mat]], self.nqubit) ham += J_xx * make_fullgate( [[i, Z_mat], [(i + 1) % self.nqubit, Z_mat]], self.nqubit) diag, eigen_vecs = np.linalg.eigh(ham) time_evol_op = np.dot( np.dot(eigen_vecs, np.diag(np.exp(-1j * self.time_step * diag))), eigen_vecs.T.conj()) time_evol_gate = DenseMatrix([i for i in range(self.nqubit)], time_evol_op) u.add_gate(time_evol_gate) elif uin_type == 60: #Heisenberg hamiltonian with input coefficient # every two possible spin-conbination has interaction for i in range(self.nqubit): u.add_RX_gate(i, -2 * x[i] * self.time_step) for j in range(i + 1, self.nqubit): XX(u, theta[i] * theta[j], i, j) YY(u, theta[i] * theta[j], i, j) ZZ(u, theta[i] * theta[j], i, j) elif uin_type == 61: ham = np.zeros((2**self.nqubit, 2**self.nqubit), dtype=complex) for i in range(self.nqubit): J_x = x[i] ham += J_x * make_fullgate([[i, X_mat]], self.nqubit) for j in range(i + 1, self.nqubit): J_xx = x[i] * x[j] J_yy = x[i] * x[j] J_zz = x[i] * x[j] ham += J_xx * make_fullgate([[i, X_mat], [j, X_mat]], self.nqubit) ham += J_yy * make_fullgate([[i, Y_mat], [j, Y_mat]], self.nqubit) ham += J_xx * make_fullgate([[i, Z_mat], [j, Z_mat]], self.nqubit) diag, eigen_vecs = np.linalg.eigh(ham) time_evol_op = np.dot( np.dot(eigen_vecs, np.diag(np.exp(-1j * self.time_step * diag))), eigen_vecs.T.conj()) time_evol_gate = DenseMatrix([i for i in range(self.nqubit)], time_evol_op) u.add_gate(time_evol_gate) else: pass return u