def test_mc_dtypes2(): "Monte-carlo: check for correct dtypes (average_states=False)" # set system parameters kappa = 2.0 # mirror coupling gamma = 0.2 # spontaneous emission rate g = 1 # atom/cavity coupling strength wc = 0 # cavity frequency w0 = 0 # atom frequency wl = 0 # driving frequency E = 0.5 # driving amplitude N = 5 # number of cavity energy levels (0->3 Fock states) tlist = np.linspace(0, 10, 5) # times for expectation values # construct Hamiltonian ida = qeye(N) idatom = qeye(2) a = tensor(destroy(N), idatom) sm = tensor(ida, sigmam()) H = (w0 - wl) * sm.dag() * sm + (wc - wl) * a.dag() * a + \ 1j * g * (a.dag() * sm - sm.dag() * a) + E * (a.dag() + a) # collapse operators C1 = np.sqrt(2 * kappa) * a C2 = np.sqrt(gamma) * sm C1dC1 = C1.dag() * C1 C2dC2 = C2.dag() * C2 # intial state psi0 = tensor(basis(N, 0), basis(2, 1)) opts = Options(average_expect=False) data = mcsolve(H, psi0, tlist, [C1, C2], [C1dC1, C2dC2, a], ntraj=5, options=opts) assert_equal(isinstance(data.expect[0][0][1], float), True) assert_equal(isinstance(data.expect[0][1][1], float), True) assert_equal(isinstance(data.expect[0][2][1], complex), True)
def test_underdamped_pure_dephasing_model_underdamped_bath( self, atol=1e-3): udm = UnderdampedPureDephasingModel( lam=0.1, gamma=0.05, w0=1, T=1 / 0.95, Nk=2, ) bath = UnderDampedBath( Q=udm.Q, lam=udm.lam, T=udm.T, Nk=udm.Nk, gamma=udm.gamma, w0=udm.w0, ) options = Options(nsteps=15000, store_states=True) hsolver = HEOMSolver(udm.H, bath, 14, options=options) tlist = np.linspace(0, 10, 21) result = hsolver.run(udm.rho(), tlist) test = udm.state_results(result.states) expected = udm.analytic_results(tlist) np.testing.assert_allclose(test, expected, atol=atol) rho_final, ado_state = hsolver.steady_state() test = udm.state_results([rho_final]) expected = udm.analytic_results([5000]) np.testing.assert_allclose(test, expected, atol=atol) assert rho_final == ado_state.extract(0)
def test_discrete_level_model_fermionic_bath(self, evo, liouvillianize): dlm = DiscreteLevelCurrentModel( gamma=0.01, W=1, T=0.025851991, lmax=10, ) H_sys = hamiltonian_to_sys(dlm.H, evo, liouvillianize) ck_plus, vk_plus, ck_minus, vk_minus = dlm.bath_coefficients() options = Options( nsteps=15_000, store_states=True, rtol=1e-7, atol=1e-7, ) bath = FermionicBath(dlm.Q, ck_plus, vk_plus, ck_minus, vk_minus) # for a single impurity we converge with max_depth = 2 hsolver = HEOMSolver(H_sys, bath, 2, options=options) tlist = [0, 600] result = hsolver.run(dlm.rho(), tlist, ado_return=True) current = dlm.state_current(result.ado_states[-1]) analytic_current = dlm.analytic_current() np.testing.assert_allclose(analytic_current, current, rtol=1e-3) rho_final, ado_state = hsolver.steady_state() current = dlm.state_current(ado_state) analytic_current = dlm.analytic_current() np.testing.assert_allclose(analytic_current, current, rtol=1e-3)
def test_pure_dephasing_model_bosonic_bath(self, evo, combine, liouvillianize, atol=1e-3): dlm = DrudeLorentzPureDephasingModel( lam=0.025, gamma=0.05, T=1 / 0.95, Nk=2, ) ck_real, vk_real, ck_imag, vk_imag = dlm.bath_coefficients() H_sys = hamiltonian_to_sys(dlm.H, evo, liouvillianize) bath = BosonicBath(dlm.Q, ck_real, vk_real, ck_imag, vk_imag) options = Options(nsteps=15000, store_states=True) hsolver = HEOMSolver(H_sys, bath, 14, options=options) tlist = np.linspace(0, 10, 21) result = hsolver.run(dlm.rho(), tlist) test = dlm.state_results(result.states) expected = dlm.analytic_results(tlist) np.testing.assert_allclose(test, expected, atol=atol) rho_final, ado_state = hsolver.steady_state() test = dlm.state_results([rho_final]) expected = dlm.analytic_results([100]) np.testing.assert_allclose(test, expected, atol=atol) assert rho_final == ado_state.extract(0)
def __init__(self, phi_init, phi_tgt, args=[0., 0.]): """ """ self.options_evolve = Options(store_states=True) self.phi_tgt = phi_tgt self.phi_init = phi_init self.T = 1 self.set_H([0., 0.]) self.all_e = [sigmax(), sigmay(), sigmaz()]
def solve(self): # noinspection PyTypeChecker self.solve_result = sesolve( self.get_hamiltonian(), self.psi_0, self.t_list, # e_ops=get_exp_list(self.N)[2], options=Options(store_states=True, nsteps=100000), # ntraj=2 )
def solve(L, rho0, tlist, options=None, e=0.8): """ Solve the Lindblad equation given initial density matrix and time. """ if options is None: options = Options() states = [] states.append(rho0) n = rho0.shape[0] a = destroy(n) mean_photon_number = expect(a.dag() * a, rho0) dt = np.diff(tlist) rho = rho0.full().ravel("F") rho = rho.flatten() L = csr_matrix(L.full()) r = ode(cy_ode_rhs) r.set_f_params(L.data, L.indices, L.indptr) r.set_integrator( "zvode", method=options.method, order=options.order, atol=options.atol, rtol=options.rtol, nsteps=options.nsteps, first_step=options.first_step, min_step=options.min_step, max_step=options.max_step, ) r.set_initial_value(rho, tlist[0]) n_tsteps = len(tlist) for t_idx, t in enumerate(tlist): if t_idx < n_tsteps - 1: r.integrate(r.t + dt[t_idx]) r1 = r.y.reshape((n, n)) r1_q = Qobj(r1) states.append(r1_q) mphoton_number = np.real(expect(a.dag() * a, r1_q)) if mphoton_number < e * mean_photon_number: break return states
def __init__(self, H, tlist, options=None): self.H = H self.tlist = tlist if options is None: self.options = Options(nsteps=10000, normalize_output=False) else: self.options = options # Make a blank nested dictionary to store propagators self.propagators = dict.fromkeys(tlist) for t in tlist: self.propagators[t] = dict.fromkeys(tlist)
def __init__(self, dynmaps=None, times=[], learningtimes=[], thres=0.0, options=None): if options is None: options = Options() self.dynmaps = dynmaps self.times = times self.learningtimes = learningtimes self.thres = thres self.store_states = options.store_states
def add_photon_noise(rho0, gamma, tlist): """ """ n = rho0.shape[0] a = destroy(n) c_ops = [ gamma * a, ] H = -0 * (a.dag() + a) opts = Options(atol=1e-20, store_states=True, nsteps=1500) L = liouvillian(H, c_ops=c_ops) states = mesolve(H, rho0, tlist, c_ops=c_ops) return states.states
def run_walker(self, initial_quantum_state, time_samples, dt=1e-2, observables=[], opts=Options(store_states=False, store_final_state=True)): """ Run the walker on the graph. The solver for the Lindblad master equation is mesolve from QuTip. Parameters ---------- initial_quantum_state : qutip.qobj.Qobj or integer specifying the initial node quantum state of the system at the beginning of the simulation time_samples : integer number of time samples considered in the time equation dt : float (default 10**-2) single step time interval observables: list (default empty) list of observables to track during the dynamics. opts: qutip.Options (default None) options for QuTip's solver mesolve. Returns ------- (qutip.Result) return the final quantum state at the end of the quantum simulation. """ times = np.arange(1, time_samples + 1) * dt # timesteps of the evolution # if the initial quantum state is specified as a node create the corresponding density matrix if type(initial_quantum_state) == int: density_matrix_value = np.zeros((self.N, self.N)) density_matrix_value[initial_quantum_state, initial_quantum_state] = 1 initial_quantum_state = Qobj(density_matrix_value) # if a sink is present add it to the density matrix of the system if self.sink_node is not None and initial_quantum_state.shape == ( self.N, self.N): initial_quantum_state = Qobj( np.pad(initial_quantum_state.data.toarray(), [(0, 1), (0, 1)], 'constant')) return mesolve(self.quantum_hamiltonian, initial_quantum_state, times, self.classical_hamiltonian, observables, options=opts)
def test_discrete_level_model_lorentzian_baths(self, bath_cls, analytic_current, atol=1e-3): dlm = DiscreteLevelCurrentModel( gamma=0.01, W=1, T=0.025851991, lmax=10, ) options = Options( nsteps=15_000, store_states=True, rtol=1e-7, atol=1e-7, ) bath_l = bath_cls( dlm.Q, gamma=dlm.gamma, w=dlm.W, T=dlm.T, mu=dlm.theta / 2, Nk=dlm.lmax, ) bath_r = bath_cls( dlm.Q, gamma=dlm.gamma, w=dlm.W, T=dlm.T, mu=-dlm.theta / 2, Nk=dlm.lmax, ) # for a single impurity we converge with max_depth = 2 hsolver = HEOMSolver(dlm.H, [bath_r, bath_l], 2, options=options) tlist = [0, 600] result = hsolver.run(dlm.rho(), tlist, ado_return=True) current = dlm.state_current(result.ado_states[-1]) # analytic_current = dlm.analytic_current() np.testing.assert_allclose(analytic_current, current, rtol=1e-3) rho_final, ado_state = hsolver.steady_state() current = dlm.state_current(ado_state) # analytic_current = dlm.analytic_current() np.testing.assert_allclose(analytic_current, current, rtol=1e-3)
def test_integration_error(self): dlm = DrudeLorentzPureDephasingModel( lam=0.025, gamma=0.05, T=1 / 0.95, Nk=2, ) ck_real, vk_real, ck_imag, vk_imag = dlm.bath_coefficients() bath = BosonicBath(dlm.Q, ck_real, vk_real, ck_imag, vk_imag) options = Options(nsteps=10) hsolver = HEOMSolver(dlm.H, bath, 14, options=options) with pytest.raises(RuntimeError) as err: hsolver.run(dlm.rho(), tlist=[0, 10]) assert str(err.value) == ( "HEOMSolver ODE integration error. Try increasing the nsteps given" " in the HEOMSolver options (which increases the allowed substeps" " in each step between times given in tlist).")
def test_pure_dephasing_model( self, bnd_cut_approx, atol, evo, combine, liouvillianize, ): dlm = DrudeLorentzPureDephasingModel( lam=0.025, gamma=0.05, T=1 / 0.95, Nk=2, ) ck_real, vk_real, ck_imag, vk_imag = dlm.bath_coefficients() H_sys = hamiltonian_to_sys(dlm.H, evo, liouvillianize) options = Options(nsteps=15_000, store_states=True) hsolver = HSolverDL(H_sys, dlm.Q, dlm.lam, dlm.T, 14, 2, dlm.gamma, bnd_cut_approx=bnd_cut_approx, options=options, combine=combine) tlist = np.linspace(0, 10, 21) result = hsolver.run(dlm.rho(), tlist) test = dlm.state_results(result.states) expected = dlm.analytic_results(tlist) np.testing.assert_allclose(test, expected, atol=atol) rho_final, ado_state = hsolver.steady_state() test = dlm.state_results([rho_final]) expected = dlm.analytic_results([100]) np.testing.assert_allclose(test, expected, atol=atol) assert rho_final == ado_state.extract(0)
def test_mc_seed_reuse(): "Monte-carlo: check reusing seeds" N0 = 6 N1 = 6 N2 = 6 # damping rates gamma0 = 0.1 gamma1 = 0.4 gamma2 = 0.1 alpha = np.sqrt(2) # initial coherent state param for mode 0 tlist = np.linspace(0, 10, 2) ntraj = 500 # number of trajectories # define operators a0 = tensor(destroy(N0), qeye(N1), qeye(N2)) a1 = tensor(qeye(N0), destroy(N1), qeye(N2)) a2 = tensor(qeye(N0), qeye(N1), destroy(N2)) # number operators for each mode num0 = a0.dag() * a0 num1 = a1.dag() * a1 num2 = a2.dag() * a2 # dissipative operators for zero-temp. baths C0 = np.sqrt(2.0 * gamma0) * a0 C1 = np.sqrt(2.0 * gamma1) * a1 C2 = np.sqrt(2.0 * gamma2) * a2 # initial state: coherent mode 0 & vacuum for modes #1 & #2 psi0 = tensor(coherent(N0, alpha), basis(N1, 0), basis(N2, 0)) # trilinear Hamiltonian H = 1j * (a0 * a1.dag() * a2.dag() - a0.dag() * a1 * a2) # run Monte-Carlo data1 = mcsolve(H, psi0, tlist, [C0, C1, C2], [num0, num1, num2], ntraj=ntraj) data2 = mcsolve(H, psi0, tlist, [C0, C1, C2], [num0, num1, num2], ntraj=ntraj, options=Options(seeds=data1.seeds)) for k in range(ntraj): assert_equal(np.allclose(data1.col_times[k], data2.col_times[k]), True) assert_equal(np.allclose(data1.col_which[k], data2.col_which[k]), True)
def test_MCSimpleConstStates(): "Monte-carlo: Constant H with constant collapse (states)" N = 10 # number of basis states to consider a = destroy(N) H = a.dag() * a psi0 = basis(N, 9) # initial state kappa = 0.2 # coupling to oscillator c_op_list = [np.sqrt(kappa) * a] tlist = np.linspace(0, 10, 100) mcdata = mcsolve(H, psi0, tlist, c_op_list, [], ntraj=ntraj, options=Options(average_states=True)) assert_(len(mcdata.states) == len(tlist)) assert_(isinstance(mcdata.states[0], Qobj)) expt = expect(a.dag() * a, mcdata.states) actual_answer = 9.0 * np.exp(-kappa * tlist) avg_diff = np.mean(abs(actual_answer - expt) / actual_answer) assert_equal(avg_diff < mc_error, True)
def __init__(self, processor, options=None, schedule=True): """ Args: processor (qutip.qip.device.Processor): The simulation model in qutip. E.g. LinearSpinchain, CavityQED, CircuitQED options: (qutip.Options): The option class object for the QuTiP solver. """ BasicEngine.__init__(self) self.processor = processor self._reset() self.qasm = "" self._allocated_qubits = set() if options is None: self.options = Options() else: self.options = options self.final_state = None self.schedule = schedule
def test_hsolverdl_backwards_compatibility(self, bnd_cut_approx, tol): # This is an exact copy of the pre-4.7 QuTiP HSolverDL test and # is repeated here to ensure the new HSolverDL remains compatibile # with the old one until it is removed. cut_frequency = 0.05 coupling_strength = 0.025 lam_c = coupling_strength / np.pi temperature = 1 / 0.95 times = np.linspace(0, 10, 21) def _integrand(omega, t): J = 2 * lam_c * omega * cut_frequency / (omega**2 + cut_frequency**2) return (-4 * J * (1 - np.cos(omega * t)) / (np.tanh(0.5 * omega / temperature) * omega**2)) # Calculate the analytical results by numerical integration expected = [ 0.5 * np.exp(quad(_integrand, 0, np.inf, args=(t, ), limit=5000)[0]) for t in times ] H_sys = Qobj(np.zeros((2, 2))) Q = sigmaz() initial_state = 0.5 * Qobj(np.ones((2, 2))) projector = basis(2, 0) * basis(2, 1).dag() options = Options(nsteps=15_000, store_states=True) hsolver = HSolverDL(H_sys, Q, coupling_strength, temperature, 20, 2, cut_frequency, bnd_cut_approx=bnd_cut_approx, options=options) test = expect(hsolver.run(initial_state, times).states, projector) np.testing.assert_allclose(test, expected, atol=tol)
def test_pure_dephasing_model_drude_lorentz_baths(self, terminator, bath_cls, atol=1e-3): dlm = DrudeLorentzPureDephasingModel( lam=0.025, gamma=0.05, T=1 / 0.95, Nk=2, ) bath = bath_cls( Q=dlm.Q, lam=dlm.lam, gamma=dlm.gamma, T=dlm.T, Nk=dlm.Nk, ) if terminator: _, terminator_op = bath.terminator() H_sys = liouvillian(dlm.H) + terminator_op else: H_sys = dlm.H options = Options(nsteps=15000, store_states=True) hsolver = HEOMSolver(H_sys, bath, 14, options=options) tlist = np.linspace(0, 10, 21) result = hsolver.run(dlm.rho(), tlist) test = dlm.state_results(result.states) expected = dlm.analytic_results(tlist) np.testing.assert_allclose(test, expected, atol=atol) rho_final, ado_state = hsolver.steady_state() test = dlm.state_results([rho_final]) expected = dlm.analytic_results([100]) np.testing.assert_allclose(test, expected, atol=atol) assert rho_final == ado_state.extract(0)
def test_MCNoCollExpectStates(): "Monte-carlo: Constant H with no collapse ops (expect and states)" error = 1e-8 N = 10 # number of basis states to consider a = destroy(N) H = a.dag() * a psi0 = basis(N, 9) # initial state c_op_list = [] tlist = np.linspace(0, 10, 100) mcdata = mcsolve(H, psi0, tlist, c_op_list, [a.dag() * a], ntraj=ntraj, options=Options(store_states=True)) actual_answer = 9.0 * np.ones(len(tlist)) expt = mcdata.expect[0] diff = np.mean(abs(actual_answer - expt) / actual_answer) assert_equal(diff < error, True) assert_(len(mcdata.states) == len(tlist)) assert_(isinstance(mcdata.states[0], Qobj)) expt = expect(a.dag() * a, mcdata.states) diff = np.mean(abs(actual_answer - expt) / actual_answer) assert_equal(diff < error, True)
# Since our gamma variable cannot be directly applied onto # the Lindblad operator, we must multiply it with # the collapse operators: rho0 = Qobj(L1) L1 = Qobj(gammaL * L1) L2 = Qobj(gammaL * L2) L3 = Qobj(gammaL * L3) L4 = Qobj(gammaL * L4) L5 = Qobj(gammaL * L5) L6 = Qobj(gammaL * L6) L7 = Qobj(gammaL * L7) options = Options(nsteps=1000000, atol=1e-5) bra3 = [[0, 0, 1, 0, 0, 0, 0]] bra3q = Qobj(bra3) ket3 = [[0], [0], [1], [0], [0], [0], [0]] ket3q = Qobj(ket3) starttime = 0 # this is effectively just a label - `mesolve` alwasys starts from `rho0` - # it's just saying what we're going to call the time at t0 endtime = 100 # Arbitrary - this solves with the options above # (max 1 million iterations to converge - tolerance 1e-10) num_intermediate_state = 100
def rcsolve(Hsys, psi0, tlist, e_ops, Q, wc, alpha, N, w_th, sparse=False, options=None): """ Function to solve for an open quantum system using the reaction coordinate (RC) model. Parameters ---------- Hsys: Qobj The system hamiltonian. psi0: Qobj Initial state of the system. tlist: List. Time over which system evolves. e_ops: list of :class:`qutip.Qobj` / callback function single Single operator or list of operators for which to evaluate expectation values. Q: Qobj The coupling between system and bath. wc: Float Cutoff frequency. alpha: Float Coupling strength. N: Integer Number of cavity fock states. w_th: Float Temperature. sparse: Boolean Optional argument to call the sparse eigenstates solver if needed. options : :class:`qutip.Options` With options for the solver. Returns ------- output: Result System evolution. """ if options is None: options = Options() dot_energy, dot_state = Hsys.eigenstates(sparse=sparse) deltaE = dot_energy[1] - dot_energy[0] if (w_th < deltaE / 2): warnings.warn("Given w_th might not provide accurate results") gamma = deltaE / (2 * np.pi * wc) wa = 2 * np.pi * gamma * wc # reaction coordinate frequency g = np.sqrt(np.pi * wa * alpha / 2.0) # reaction coordinate coupling nb = (1 / (np.exp(wa / w_th) - 1)) # Reaction coordinate hamiltonian/operators dimensions = dims(Q) a = tensor(destroy(N), qeye(dimensions[1])) unit = tensor(qeye(N), qeye(dimensions[1])) Nmax = N * dimensions[1][0] Q_exp = tensor(qeye(N), Q) Hsys_exp = tensor(qeye(N), Hsys) e_ops_exp = [tensor(qeye(N), kk) for kk in e_ops] na = a.dag() * a xa = a.dag() + a # decoupled Hamiltonian H0 = wa * a.dag() * a + Hsys_exp # interaction H1 = (g * (a.dag() + a) * Q_exp) H = H0 + H1 L = 0 PsipreEta = 0 PsipreX = 0 all_energy, all_state = H.eigenstates(sparse=sparse) Apre = spre((a + a.dag())) Apost = spost(a + a.dag()) for j in range(Nmax): for k in range(Nmax): A = xa.matrix_element(all_state[j].dag(), all_state[k]) delE = (all_energy[j] - all_energy[k]) if abs(A) > 0.0: if abs(delE) > 0.0: X = (0.5 * np.pi * gamma * (all_energy[j] - all_energy[k]) * (np.cosh( (all_energy[j] - all_energy[k]) / (2 * w_th)) / (np.sinh( (all_energy[j] - all_energy[k]) / (2 * w_th)))) * A) eta = (0.5 * np.pi * gamma * (all_energy[j] - all_energy[k]) * A) PsipreX = PsipreX + X * all_state[j] * all_state[k].dag() PsipreEta = PsipreEta + (eta * all_state[j] * all_state[k].dag()) else: X = 0.5 * np.pi * gamma * A * 2 * w_th PsipreX = PsipreX + X * all_state[j] * all_state[k].dag() A = a + a.dag() L = ((-spre(A * PsipreX)) + (sprepost(A, PsipreX)) + (sprepost(PsipreX, A)) + (-spost(PsipreX * A)) + (spre(A * PsipreEta)) + (sprepost(A, PsipreEta)) + (-sprepost(PsipreEta, A)) + (-spost(PsipreEta * A))) # Setup the operators and the Hamiltonian and the master equation # and solve for time steps in tlist rho0 = (tensor(thermal_dm(N, nb), psi0)) output = mesolve(H, rho0, tlist, [L], e_ops_exp, options=options) return output
H_hopping = osum([ad(n + 1) * a_(n) + ad(n) * a_(n + 1) for n in range(L - 1)]) H_bcs = osum([a_(n) * a_(n + 1) + ad(n + 1) * ad(n) for n in range(L - 1)]) H = lambda mu, t, d: -0.5 * mu * H_trivial - t * H_hopping + d * H_bcs # check the energy of the trivial regime energy_trivial = expect(H(2., 0., 0.), filled) print('Energy of the trivial regime is', energy_trivial) # prepare the measurement operators indices, measure_operators = prepareMeasurementOperators(L) # prepare the simulation tau = 10. * np.pi resolution = 300 times = np.linspace(0., tau, resolution) opts = Options(store_final_state=True) psi0 = filled fidelities = measure(psi0, measure_operators) plotMeasurement(L, indices, fidelities, filename='plots/mzms/psi0', title=r'$\left\vert \psi_0 \right\rangle$') H0 = -0.5 * (2 * ad(0) * a_(0) + 2 * ad(1) * a_(1) + 2 * ad(2) * a_(2) - 3) Hf = -0.5 * (2 * ad(0) * a_(0) + 2 * ad(1) * a_(1) - 1) Ht = lambda t, args: (1 - t / tau) * H0 + (t / tau) * Hf psi1 = mesolve(Ht, psi0, times, options=opts).final_state fidelities = measure(psi1, measure_operators) plotMeasurement(L,
def hsolve(H, psi0, tlist, Q, gam, lam0, Nc, N, w_th, options=None): """ Function to solve for an open quantum system using the hierarchy model. Parameters ---------- H: Qobj The system hamiltonian. psi0: Qobj Initial state of the system. tlist: List. Time over which system evolves. Q: Qobj The coupling between system and bath. gam: Float Bath cutoff frequency. lam0: Float Coupling strength. Nc: Integer Cutoff parameter. N: Integer Number of matsubara terms. w_th: Float Temperature. options : :class:`qutip.Options` With options for the solver. Returns ------- output: Result System evolution. """ if options is None: options = Options() # Set up terms of the matsubara and tanimura boundaries # Parameters and hamiltonian hbar = 1. kb = 1. # Set by system dimensions = dims(H) Nsup = dimensions[0][0] * dimensions[0][0] unit = qeye(dimensions[0]) # Ntot is the total number of ancillary elements in the hierarchy Ntot = int(round(factorial(Nc+N) / (factorial(Nc) * factorial(N)))) c0 = (lam0 * gam * (_cot(gam * hbar / (2. * kb * w_th)) - (1j))) / hbar LD1 = (-2. * spre(Q) * spost(Q.dag()) + spre(Q.dag()*Q) + spost(Q.dag()*Q)) pref = ((2. * lam0 * kb * w_th / (gam * hbar)) - 1j * lam0) / hbar gj = 2 * np.pi * kb * w_th / hbar L12 = -pref * LD1 + (c0 / gam) * LD1 for i1 in range(1, N): num = (4 * lam0 * gam * kb * w_th * i1 * gj/((i1 * gj)**2 - gam**2)) ci = num / (hbar**2) L12 = L12 + (ci / gj) * LD1 # Setup liouvillian L = liouvillian(H, [L12]) Ltot = L.data unit = sp.eye(Ntot,format='csr') Lbig = sp.kron(unit, Ltot) rho0big1 = np.zeros((Nsup * Ntot), dtype=complex) # Prepare initial state: rhotemp = mat2vec(np.array(psi0.full(), dtype=complex)) for idx, element in enumerate(rhotemp): rho0big1[idx] = element[0] nstates, state2idx, idx2state = enr_state_dictionaries([Nc+1]*(N), Nc) for nlabelt in state_number_enumerate([Nc+1]*(N), Nc): nlabel = list(nlabelt) ntotalcheck = 0 for ncheck in range(N): ntotalcheck = ntotalcheck + nlabel[ncheck] current_pos = int(round(state2idx[tuple(nlabel)])) Ltemp = sp.lil_matrix((Ntot, Ntot)) Ltemp[current_pos, current_pos] = 1 Ltemp.tocsr() Lbig = Lbig + sp.kron(Ltemp, (-nlabel[0] * gam * spre(unit).data)) for kcount in range(1, N): counts = -nlabel[kcount] * kcount * gj * spre(unit).data Lbig = Lbig + sp.kron(Ltemp, counts) for kcount in range(N): if nlabel[kcount] >= 1: # find the position of the neighbour nlabeltemp = copy(nlabel) nlabel[kcount] = nlabel[kcount] - 1 current_pos2 = int(round(state2idx[tuple(nlabel)])) Ltemp = sp.lil_matrix((Ntot, Ntot)) Ltemp[current_pos, current_pos2] = 1 Ltemp.tocsr() # renormalized version: ci = (4 * lam0 * gam * kb * w_th * kcount * gj/((kcount * gj)**2 - gam**2)) / (hbar**2) if kcount == 0: Lbig = Lbig + sp.kron(Ltemp, (-1j * (np.sqrt(nlabeltemp[kcount] / abs(c0))) * ((c0) * spre(Q).data - (np.conj(c0)) * spost(Q).data))) if kcount > 0: ci = (4 * lam0 * gam * kb * w_th * kcount * gj/((kcount * gj)**2 - gam**2)) / (hbar**2) Lbig = Lbig + sp.kron(Ltemp, (-1j * (np.sqrt(nlabeltemp[kcount] / abs(ci))) * ((ci) * spre(Q).data - (np.conj(ci)) * spost(Q).data))) nlabel = copy(nlabeltemp) for kcount in range(N): if ntotalcheck <= (Nc-1): nlabeltemp = copy(nlabel) nlabel[kcount] = nlabel[kcount] + 1 current_pos3 = int(round(state2idx[tuple(nlabel)])) if current_pos3 <= (Ntot): Ltemp = sp.lil_matrix((Ntot, Ntot)) Ltemp[current_pos, current_pos3] = 1 Ltemp.tocsr() # renormalized if kcount == 0: Lbig = Lbig + sp.kron(Ltemp, -1j * (np.sqrt((nlabeltemp[kcount]+1) * abs(c0))) * (spre(Q) - spost(Q)).data) if kcount > 0: ci = (4 * lam0 * gam * kb * w_th * kcount * gj/((kcount * gj)**2 - gam**2)) / (hbar**2) Lbig = Lbig + sp.kron(Ltemp, -1j * (np.sqrt((nlabeltemp[kcount]+1) * abs(ci))) * (spre(Q) - spost(Q)).data) nlabel = copy(nlabeltemp) output = [] for element in rhotemp: output.append([]) r = scipy.integrate.ode(cy_ode_rhs) Lbig2 = Lbig.tocsr() r.set_f_params(Lbig2.data, Lbig2.indices, Lbig2.indptr) r.set_integrator('zvode', method=options.method, order=options.order, atol=options.atol, rtol=options.rtol, nsteps=options.nsteps, first_step=options.first_step, min_step=options.min_step, max_step=options.max_step) r.set_initial_value(rho0big1, tlist[0]) dt = tlist[1] - tlist[0] for t_idx, t in enumerate(tlist): r.integrate(r.t + dt) for idx, element in enumerate(rhotemp): output[idx].append(r.y[idx]) return output
def evolve(H, t, psi, res=200, c_ops=[]): opts = Options(store_final_state=True) times = np.linspace(0., t, res) result = mesolve(H, psi, times, c_ops, options=opts) return result.final_state
def _test_evolve_lindblad_discrete(): """ Run end-to-end tests on evolve_lindblad_discrete. """ import numpy as np from qutip import mesolve, Qobj, Options from qoc.standard import ( conjugate_transpose, SIGMA_X, SIGMA_Y, matrix_to_column_vector_list, SIGMA_PLUS, SIGMA_MINUS, ) def _generate_complex_matrix(matrix_size): return (np.random.rand(matrix_size, matrix_size) + 1j * np.random.rand(matrix_size, matrix_size)) def _generate_hermitian_matrix(matrix_size): matrix = _generate_complex_matrix(matrix_size) return (matrix + conjugate_transpose(matrix)) * 0.5 # Test that evolution WITH a hamiltonian and WITHOUT lindblad operators # yields a known result. # Use e.q. 109 from # https://arxiv.org/pdf/1904.06560.pdf. hilbert_size = 4 identity_matrix = np.eye(hilbert_size, dtype=np.complex128) iswap_unitary = np.array( ((1, 0, 0, 0), (0, 0, -1j, 0), (0, -1j, 0, 0), (0, 0, 0, 1))) initial_states = matrix_to_column_vector_list(identity_matrix) target_states = matrix_to_column_vector_list(iswap_unitary) initial_densities = np.matmul(initial_states, conjugate_transpose(initial_states)) target_densities = np.matmul(target_states, conjugate_transpose(target_states)) system_hamiltonian = ( (1 / 2) * (np.kron(SIGMA_X, SIGMA_X) + np.kron(SIGMA_Y, SIGMA_Y))) hamiltonian = lambda controls, time: system_hamiltonian control_step_count = int(1e3) evolution_time = np.pi / 2 result = evolve_lindblad_discrete(control_step_count, evolution_time, initial_densities, hamiltonian=hamiltonian) final_densities = result.final_densities assert (np.allclose(final_densities, target_densities)) # Note that qutip only gets this result within 1e-5 error. tlist = np.linspace(0, evolution_time, control_step_count) c_ops = list() e_ops = list() options = Options(nsteps=control_step_count) for i, initial_density in enumerate(initial_densities): result = mesolve(Qobj(system_hamiltonian), Qobj(initial_density), tlist, c_ops, e_ops, options=options) final_density = result.states[-1].full() target_density = target_densities[i] assert (np.allclose(final_density, target_density, atol=1e-5)) #ENDFOR # Test that evolution WITHOUT a hamiltonian and WITH lindblad operators # yields a known result. # This test ensures that dissipators are working correctly. # Use e.q.14 from # https://inst.eecs.berkeley.edu/~cs191/fa14/lectures/lecture15.pdf. hilbert_size = 2 gamma = 2 lindblad_dissipators = np.array((gamma, )) lindblad_operators = np.stack((SIGMA_MINUS, )) lindblad_data = lambda time: (lindblad_dissipators, lindblad_operators) evolution_time = 1. control_step_count = int(1e3) inv_sqrt_2 = 1 / np.sqrt(2) a0 = np.random.rand() c0 = 1 - a0 b0 = np.random.rand() b0_star = np.conj(b0) initial_density_0 = np.array(((a0, b0), (b0_star, c0))) initial_densities = np.stack((initial_density_0, )) gt = gamma * evolution_time expected_final_density = np.array( ((1 - c0 * np.exp(-gt), b0 * np.exp(-gt / 2)), (b0_star * np.exp(-gt / 2), c0 * np.exp(-gt)))) result = evolve_lindblad_discrete(control_step_count, evolution_time, initial_densities, lindblad_data=lindblad_data) final_density = result.final_densities[0] assert (np.allclose(final_density, expected_final_density)) # Test that evolution WITH a random hamiltonian and WITH random lindblad operators # yields a similar result to qutip. # Note that the allclose tolerance may need to be adjusted. for matrix_size in range(2, _BIG): # Evolve under lindbladian. hamiltonian_matrix = _generate_hermitian_matrix(matrix_size) hamiltonian = lambda controls, time: hamiltonian_matrix lindblad_operator_count = np.random.randint(1, matrix_size) lindblad_operators = np.stack([ _generate_complex_matrix(matrix_size) for _ in range(lindblad_operator_count) ]) lindblad_dissipators = np.ones((lindblad_operator_count)) lindblad_data = lambda time: (lindblad_dissipators, lindblad_operators) density_matrix = _generate_hermitian_matrix(matrix_size) initial_densities = np.stack((density_matrix, )) evolution_time = 1 control_step_count = int(1e4) result = evolve_lindblad_discrete(control_step_count, evolution_time, initial_densities, hamiltonian=hamiltonian, lindblad_data=lindblad_data) final_density = result.final_densities[0] # Evolve under lindbladian with qutip. hamiltonian_qutip = Qobj(hamiltonian_matrix) initial_density_qutip = Qobj(density_matrix) lindblad_operators_qutip = [ Qobj(lindblad_operator) for lindblad_operator in lindblad_operators ] e_ops_qutip = list() tlist = np.linspace(0, evolution_time, control_step_count) options = Options(nsteps=control_step_count) result_qutip = mesolve( hamiltonian_qutip, initial_density_qutip, tlist, lindblad_operators_qutip, e_ops_qutip, ) final_density_qutip = result_qutip.states[-1].full() assert (np.allclose(final_density, final_density_qutip, atol=1e-6))
def test_ado_return_and_ado_init(self, ado_format): dlm = DrudeLorentzPureDephasingModel( lam=0.025, gamma=0.05, T=1 / 0.95, Nk=2, ) ck_real, vk_real, ck_imag, vk_imag = dlm.bath_coefficients() bath = BosonicBath(dlm.Q, ck_real, vk_real, ck_imag, vk_imag) options = Options(nsteps=15_000, store_states=True) hsolver = HEOMSolver(dlm.H, bath, 6, options=options) tlist_1 = [0, 1, 2] result_1 = hsolver.run(dlm.rho(), tlist_1, ado_return=True) tlist_2 = [2, 3, 4] rho0 = result_1.ado_states[-1] if ado_format == "numpy": rho0 = rho0._ado_state # extract the raw numpy array result_2 = hsolver.run( rho0, tlist_2, ado_return=True, ado_init=True, ) tlist_full = tlist_1 + tlist_2[1:] result_full = hsolver.run(dlm.rho(), tlist_full, ado_return=True) times_12 = result_1.times + result_2.times[1:] times_full = result_full.times assert times_12 == tlist_full assert times_full == tlist_full ado_states_12 = result_1.ado_states + result_2.ado_states[1:] ado_states_full = result_full.ado_states assert len(ado_states_12) == len(tlist_full) assert len(ado_states_full) == len(tlist_full) for ado_12, ado_full in zip(ado_states_12, ado_states_full): for label in hsolver.ados.labels: np.testing.assert_allclose( ado_12.extract(label).full(), ado_full.extract(label).full(), atol=1e-6, ) states_12 = result_1.states + result_2.states[1:] states_full = result_full.states assert len(states_12) == len(tlist_full) assert len(states_full) == len(tlist_full) for ado_12, state_12 in zip(ado_states_12, states_12): assert ado_12.rho == state_12 for ado_full, state_full in zip(ado_states_full, states_full): assert ado_full.rho == state_full expected = dlm.analytic_results(tlist_full) test_12 = dlm.state_results(states_12) np.testing.assert_allclose(test_12, expected, atol=1e-3) test_full = dlm.state_results(states_full) np.testing.assert_allclose(test_full, expected, atol=1e-3)
from qutip import basis, fidelity from qutip import Options from custermized_qip.device import DispersiveCavityQED from custermized_qip.device import CircuitQED from custermized_qip.circuit import QubitCircuit # 定义一个circuit circuit = QubitCircuit(2) circuit.add_gate("X", targets=0) circuit.add_gate("Z", targets=0) circuit.add_gate("ISWAP", targets=[0,1]) # 定义一个processor processor = Circuit_QED(2, t1=1, t2=0.2) # 加载circuit processor.load_circuit(circuit) # 计算得到final state (初始值为零态) final_state = processor.run_state(basis([10, 2, 2]), options=Options(nsteps=10000)).states[-1] # print保真度 print(fidelity(final_state.ptrace(1), basis(2,1))) # 画pulse图 fig, ax = processor.plot_pulses() fig.savefig("testfig.png") input()
return hamiltonian # time_independent_terms = Qobj(np.zeros((2, 2))) time_independent_terms = Qobj(np.zeros((2, 2)) + V6 * 1e9 * rcrt @ rcrt.T) # time_independent_terms = Qobj(np.zeros((2, 2)) - V6 * 1e9 * rcrt @ rcrt.T - 6.8e9 * rc1t @ rc1t.T) # time_independent_terms = Qobj(np.zeros((2, 2)) + 100e6 * rcrt @ rcrt.T) Omega_coeff_terms = Qobj((rcrt @ rc1t.T + rc1t @ rcrt.T) / 2) with timer("Solving"): solver = sesolve( # get_hamiltonian, [time_independent_terms, [Omega_coeff_terms, Omega]], psi_0, t_list, options=Options(store_states=True, nsteps=20000), progress_bar=True, ) fig, (ax1, ax2, ax3) = plt.subplots(3, 1, sharex=True) i0 = [] i1 = [] for state in solver.states: _state = np.abs(state.data.toarray().flatten()) i0.append(_state[0]**2) i1.append(_state[1]**2) ax1.plot( t_list, np.array(Omegas) / 1e6,
""" This is an example using QuTiP as the backend for ProjectQ """ import numpy as np from projectq.backends import IBMBackend from projectq import MainEngine from projectq.ops import All, H, X, Z, Y, T, CNOT, Measure, FlushGate from qutip import fidelity, basis, Options options = Options(nsteps=20000, max_step=0.0001) # options for QuTiP solver from qutipbackend import QutipBackend from custermized_qip.device import CircuitQED import matplotlib.pyplot as plt plt.rcParams.update({ "font.size": 19, "text.usetex": False, # 'legend.fontsize': 'x-large', 'axes.labelsize': 'small', # 'axes.titlesize':'x-small', 'xtick.labelsize': 'x-small', 'ytick.labelsize': 'x-small', }) # Define a circuit in ProjectQ: DJ algorithm def DJ_algorith(eng): quregs = eng.allocate_qureg(num_qubits) X | quregs[2] All(H) | quregs CNOT | (quregs[0], quregs[2]) CNOT | (quregs[1], quregs[2])