def loop_u_tp(u_range, tprange, beta, seed='mott gap'): tau, w_n = gf.tau_wn_setup(dict(BETA=beta, N_MATSUBARA=max(5 * beta, 256))) giw_d, giw_o = dimer.gf_met(w_n, 0., 0., 0.5, 0.) if seed == 'mott gap': giw_d, giw_o = 1 / (1j * w_n + 4j / w_n), np.zeros_like(w_n) + 0j giw_s = [] sigma_iw = [] ekin, epot = [], [] iterations = [] for u_int, tp in zip(u_range, tprange): giw_d, giw_o, loops = dimer.ipt_dmft_loop(beta, u_int, tp, giw_d, giw_o, tau, w_n) giw_s.append((giw_d, giw_o)) iterations.append(loops) g0iw_d, g0iw_o = dimer.self_consistency(1j * w_n, 1j * giw_d.imag, giw_o.real, 0., tp, 0.25) siw_d, siw_o = ipt.dimer_sigma(u_int, tp, g0iw_d, g0iw_o, tau, w_n) sigma_iw.append((siw_d.copy(), siw_o.copy())) ekin.append(dimer.ekin(giw_d, giw_o, w_n, tp, beta)) epot.append( dimer.epot(giw_d, w_n, beta, u_int**2 / 4 + tp**2, ekin[-1], u_int) / 4) # last division because I want per spin epot print(np.array(iterations)) return np.array(giw_s), np.array(sigma_iw), np.array(ekin), np.array( epot), w_n
def loop_tp_u(tprange, u_range, beta, filestr, seed='mott gap'): save_dir = filestr.format(beta) if np.allclose(tprange, tprange[0]) and 'tp' not in save_dir: save_dir = os.path.join(save_dir, 'tp' + str(tprange[0])) elif np.allclose(u_range, u_range[0]): save_dir = os.path.join(save_dir, 'U' + str(u_range[0])) if not os.path.exists(save_dir): os.makedirs(save_dir) setup = { 'beta': beta, 'tprange': tprange.tolist(), 'u_range': u_range.tolist() } with open(save_dir + '/setup', 'w') as conf: json.dump(setup, conf, indent=2) ############################################################################### tau, w_n = gf.tau_wn_setup( dict(BETA=beta, N_MATSUBARA=max(2**ceil(log(6 * beta) / log(2)), 256))) giw_d, giw_o = dimer.gf_met(w_n, 0., tprange[0], 0.5, 0.) if seed == 'mott gap': giw_d, giw_o = 1 / (1j * w_n - 4j / w_n), np.zeros_like(w_n) + 0j giw_s = [] for tp, u_int in zip(tprange, u_range): giw_d, giw_o, loops = dimer.ipt_dmft_loop(beta, u_int, tp, giw_d, giw_o, tau, w_n, 1 / 5 / beta) giw_s.append((giw_d.imag, giw_o.real)) np.save(save_dir + '/giw', np.array(giw_s))
def test_selfconsistency(tp): """Check that the Bethe lattice self-consistency is working""" _, w_n = tau_wn_setup(dict(BETA=100., N_MATSUBARA=400)) giwd, giwo = dimer.gf_met(w_n, 0., tp, 0.5, 0.) g0iwd, g0iwo = dimer.self_consistency(1j * w_n, giwd, giwo, 0., tp, 0.25) assert np.allclose(giwd, g0iwd) assert np.allclose(giwo, g0iwo)
def test_ipt_dimer_pm_g(u_int, result, beta=50.): tau, w_n = tau_wn_setup(dict(BETA=beta, N_MATSUBARA=256)) giw_d, giw_o = dimer.gf_met(w_n, 0., 0, 0.5, 0.) giw_d = dimer.ipt_dmft_loop(beta, u_int, 0, giw_d, giw_o, tau, w_n, 1e-5)[0][:64] assert np.allclose(result, giw_d, atol=3e-3)
def loop_u_tp(u_range, tp_range, beta, seed='mott gap'): """Solves IPT dimer and return Im Sigma_AA, Re Simga_AB returns list len(betarange) x 2 Sigma arrays """ tau, w_n = gf.tau_wn_setup( dict(BETA=beta, N_MATSUBARA=max(2**ceil(log(4 * beta) / log(2)), 256))) giw_d, giw_o = dimer.gf_met(w_n, 0., 0., 0.5, 0.) if seed == 'I': giw_d, giw_o = 1 / (1j * w_n - 4j / w_n), np.zeros_like(w_n) + 0j sigma_iw = [] iterations = [] for tp, u_int in zip(tp_range, u_range): giw_d, giw_o, loops = dimer.ipt_dmft_loop(beta, u_int, tp, giw_d, giw_o, tau, w_n, 1e-3) iterations.append(loops) g0iw_d, g0iw_o = dimer.self_consistency(1j * w_n, 1j * giw_d.imag, giw_o.real, 0., tp, 0.25) siw_d, siw_o = ipt.dimer_sigma(u_int, tp, g0iw_d, g0iw_o, tau, w_n) sigma_iw.append((siw_d.imag, siw_o.real)) print(np.array(iterations)) return sigma_iw
def test_GF(): """Test the Matrix product and Matrix inversion of a 2x2 Matrix which for the case of the dimer has a symmetric structure in which only requires the first row""" _, w_n = tau_wn_setup(dict(BETA=100., N_MATSUBARA=400)) giwd, giwo = dimer.gf_met(w_n, 0., 0.25, 0.5, 0.) inv_giwd, inv_giwo = dimer.mat_inv(giwd, giwo) one, zero = dimer.mat_mul(inv_giwd, inv_giwo, giwd, giwo) assert np.allclose(one, 1.) assert np.allclose(zero, 0.)
def ipt_u_tp(u_int, tp, beta, seed="ins"): tau, w_n = gf.tau_wn_setup(dict(BETA=beta, N_MATSUBARA=1024)) giw_d, giw_o = dimer.gf_met(w_n, 0., 0., 0.5, 0.) if seed == "ins": giw_d, giw_o = 1 / (1j * w_n + 4j / w_n), np.zeros_like(w_n) + 0j giw_d, giw_o, loops = dimer.ipt_dmft_loop( beta, u_int, tp, giw_d, giw_o, tau, w_n, 1e-12) g0iw_d, g0iw_o = dimer.self_consistency( 1j * w_n, 1j * giw_d.imag, giw_o.real, 0., tp, 0.25) siw_d, siw_o = ipt.dimer_sigma(u_int, tp, g0iw_d, g0iw_o, tau, w_n) return giw_d, giw_o, siw_d, siw_o, g0iw_d, g0iw_o, w_n
def loop_urange(urange, tp, beta): ekin, epot = [], [] tau, w_n = gf.tau_wn_setup(dict(BETA=beta, N_MATSUBARA=2**10)) giw_d, giw_o = dimer.gf_met(w_n, 0., 0., 0.5, 0.) for u_int in urange: giw_d, giw_o, _ = dimer.ipt_dmft_loop(beta, u_int, tp, giw_d, giw_o, tau, w_n, 1e-4) ekin.append(dimer.ekin(giw_d, giw_o, w_n, tp, beta)) epot.append( dimer.epot(giw_d, w_n, beta, u_int**2 / 4 + tp**2 + 0.25, ekin[-1], u_int)) return np.array(ekin), np.array(epot)
def ipt_u_tp(u_int, tp, beta, seed='ins'): tau, w_n = gf.tau_wn_setup(dict(BETA=beta, N_MATSUBARA=2**8)) tau, w_n = gf.tau_wn_setup( dict(BETA=beta, N_MATSUBARA=max(2**ceil(log(8 * beta) / log(2)), 256))) giw_d, giw_o = dimer.gf_met(w_n, 0., 0., 0.5, 0.) if seed == 'ins': giw_d, giw_o = 1 / (1j * w_n + 4j / w_n), np.zeros_like(w_n) + 0j giw_d, giw_o, loops = dimer.ipt_dmft_loop( beta, u_int, tp, giw_d, giw_o, tau, w_n, 1e-7) g0iw_d, g0iw_o = dimer.self_consistency( 1j * w_n, 1j * giw_d.imag, giw_o.real, 0., tp, 0.25) siw_d, siw_o = ipt.dimer_sigma(u_int, tp, g0iw_d, g0iw_o, tau, w_n) return giw_d, giw_o, siw_d, siw_o, g0iw_d, g0iw_o, w_n
def loop_u_tp(u_range, tprange, beta, seed='mott gap'): tau, w_n = gf.tau_wn_setup(dict(BETA=beta, N_MATSUBARA=max(5 * beta, 256))) giw_d, giw_o = dimer.gf_met(w_n, 0., 0., 0.5, 0.) if seed == 'mott gap': giw_d, giw_o = 1 / (1j * w_n + 4j / w_n), np.zeros_like(w_n) + 0j sigma_iw = [] for u_int, tp in zip(u_range, tprange): giw_d, giw_o, loops = dimer.ipt_dmft_loop( beta, u_int, tp, giw_d, giw_o, tau, w_n) g0iw_d, g0iw_o = dimer.self_consistency( 1j * w_n, 1j * giw_d.imag, giw_o.real, 0., tp, 0.25) siw_d, siw_o = ipt.dimer_sigma(u_int, tp, g0iw_d, g0iw_o, tau, w_n) sigma_iw.append((siw_d.copy(), siw_o.copy())) print(seed, ' U', u_int, ' tp: ', tp, ' loops: ', loops) return np.array(sigma_iw), w_n
def loop_u_tp(u_range, tprange, beta, seed='mott gap'): tau, w_n = gf.tau_wn_setup(dict(BETA=beta, N_MATSUBARA=256)) giw_d, giw_o = dimer.gf_met(w_n, 0., 0., 0.5, 0.) if seed == 'ins': giw_d, giw_o = 1 / (1j * w_n + 4j / w_n), np.zeros_like(w_n) + 0j sols = [dmft_solve(giw_d, giw_o, u_int, tp, beta, tau, w_n) for u_int, tp in zip(u_range, tprange)] giw_s = np.array([g[0] for g in sols]) sigma_iw = np.array([g[1] for g in sols]) ekin = np.array([g[2] for g in sols]) epot = np.array([g[3] for g in sols]) iterations = np.array([g[4] for g in sols]) print(iterations) return giw_s, sigma_iw, ekin, epot, w_n
def loop_beta(u_int, tp, betarange, seed): avgH = [] for beta in betarange: tau, w_n = gf.tau_wn_setup( dict(BETA=beta, N_MATSUBARA=max(2**ceil(log(8 * beta) / log(2)), 256))) giw_d, giw_o = dimer.gf_met(w_n, 0., 0., 0.5, 0.) if seed == 'I': giw_d, giw_o = 1 / (1j * w_n - 4j / w_n), np.zeros_like(w_n) + 0j giw_d, giw_o, _ = dimer.ipt_dmft_loop( beta, u_int, tp, giw_d, giw_o, tau, w_n, 1e-6) ekin = dimer.ekin(giw_d[:int(8 * beta)], giw_o[:int(8 * beta)], w_n[:int(8 * beta)], tp, beta) epot = dimer.epot(giw_d[:int(8 * beta)], w_n[:int(8 * beta)], beta, u_int ** 2 / 4 + tp**2 + 0.25, ekin, u_int) avgH.append(ekin + epot) return np.array(avgH)
def ekin( BETA, tp=0.25, filestr='tp{tp}_B{BETA}.h5', ): e_mean = dimer.free_ekin(tp, BETA) tau, w_n = gf.tau_wn_setup(dict(BETA=BETA, N_MATSUBARA=BETA)) giw_free_d, _ = dimer.gf_met(w_n, 0., tp, 0.5, 0.) T = [] with h5.File(filestr.format(tp=tp, BETA=BETA), 'r') as results: for u_str in results: last_iter = results[u_str].keys()[-1] giwd, giwo = get_giw(results[u_str], last_iter, tau, w_n) siwd, siwo = get_sigmaiw(results[u_str], last_iter, tau, w_n) T.append(2 * (w_n * (giw_free_d - giwd).imag + giwd.imag * siwd.imag - giwo.real * siwo.real).sum() / BETA + e_mean) ur = np.array([float(u_str[1:]) for u_str in results]) return np.array(T), ur
def ipt_u_tp(urange, tp, beta, w): tau, w_n = gf.tau_wn_setup(dict(BETA=beta, N_MATSUBARA=2**11)) giw_d, giw_o = dimer.gf_met(w_n, 0., tp, 0.5, 0.) w_set = list(np.arange(0, 120, 2)) w_set = w_set + list(np.arange(120, 512, 8)) imgss = [] for u_int in urange: giw_d, giw_o, loops = dimer.ipt_dmft_loop(beta, u_int, tp, giw_d, giw_o, tau, w_n, 1e-9) g0iw_d, g0iw_o = dimer.self_consistency(1j * w_n, 1j * giw_d.imag, giw_o.real, 0., tp, 0.25) siw_d, siw_o = ipt_imag.dimer_sigma(u_int, tp, g0iw_d, g0iw_o, tau, w_n) ss = gf.pade_continuation(1j * siw_d.imag + siw_o.real, w_n, w + 0.0005j, w_set) # A-bond imgss.append( gf.semi_circle_hiltrans(w - tp - (ss.real - 1j * np.abs(ss.imag)))) return imgss
def dmft_loop_pm(simulation, U, g_iw_start=None): """Implementation of the solver""" setup = { 't': 0.5, 'BANDS': 1, 'SITES': 2, } setup.update(simulation) setup['dtau_mc'] = setup['BETA'] / 2. / setup['N_MATSUBARA'] current_u = 'U' + str(U) setup['U'] = U setup['simt'] = 'PM' # simulation type ParaMagnetic if setup['AFM']: setup['simt'] = 'AFM' # simulation type AntiFerroMagnetic tau, w_n = gf.tau_wn_setup(setup) intm = hf.interaction_matrix(setup['BANDS']) setup['n_tau_mc'] = len(tau) mu, tp = setup['MU'], setup['tp'] giw_d, giw_o = dimer.gf_met(w_n, mu, tp, 0.5, 0.) gmix = np.array([[1j * w_n + mu, -tp * np.ones_like(w_n)], [-tp * np.ones_like(w_n), 1j * w_n + mu]]) giw = np.array([[giw_d, giw_o], [giw_o, giw_d]]) g0tau0 = -0.5 * np.eye(2).reshape(2, 2, 1) gtu = gf.gw_invfouriertrans(giw, tau, w_n, pd.gf_tail(g0tau0, 0., mu, tp)) gtd = np.copy(gtu) if g_iw_start is not None: giw_up = g_iw_start[0] giw_dw = g_iw_start[1] save_dir = os.path.join(setup['ofile'].format(**setup), current_u) try: # try reloading data from disk with open(save_dir + '/setup', 'r') as conf: last_loop = json.load(conf)['last_loop'] gtu = np.load( os.path.join(save_dir, 'it{:03}'.format(last_loop), 'gtau_up.npy')).reshape(2, 2, -1) gtd = np.load( os.path.join(save_dir, 'it{:03}'.format(last_loop), 'gtau_dw.npy')).reshape(2, 2, -1) last_loop += 1 except (IOError, KeyError, ValueError): # if no data clean start last_loop = 0 V_field = hf.ising_v(setup['dtau_mc'], U, L=setup['SITES'] * setup['n_tau_mc'], polar=setup['spin_polarization']) for iter_count in range(last_loop, last_loop + setup['Niter']): work_dir = os.path.join(save_dir, 'it{:03}'.format(iter_count)) setup['work_dir'] = work_dir if comm.rank == 0: print('On loop', iter_count, 'beta', setup['BETA'], 'U', U, 'tp', tp) # paramagnetic cleaning gtu = 0.5 * (gtu + gtd) gtd = gtu giw_up = gf.gt_fouriertrans(gtu, tau, w_n, pd.gf_tail(gtu, U, mu, tp)) giw_dw = gf.gt_fouriertrans(gtd, tau, w_n, pd.gf_tail(gtd, U, mu, tp)) # Bethe lattice bath g0iw_up = dimer.mat_2_inv(gmix - 0.25 * giw_up) g0iw_dw = dimer.mat_2_inv(gmix - 0.25 * giw_dw) g0tau_up = gf.gw_invfouriertrans(g0iw_up, tau, w_n, pd.gf_tail(g0tau0, 0., mu, tp)) g0tau_dw = gf.gw_invfouriertrans(g0iw_dw, tau, w_n, pd.gf_tail(g0tau0, 0., mu, tp)) # Impurity solver gtu, gtd = hf.imp_solver([g0tau_dw, g0tau_up], V_field, intm, setup) # Save output if comm.rank == 0: np.save(work_dir + '/gtau_up', gtu.reshape(4, -1)) np.save(work_dir + '/gtau_dw', gtd.reshape(4, -1)) with open(save_dir + '/setup', 'w') as conf: setup['last_loop'] = iter_count json.dump(setup, conf, indent=2) sys.stdout.flush()
ax[1].set_xlim(-2, 2) ax[1].set_ylim(*ylim) w = np.linspace(-4, 4, 2**12) dw = w[1] - w[0] BETA = 756. tau, w_n = gf.tau_wn_setup(dict(BETA=BETA, N_MATSUBARA=2**12)) nfp = gf.fermi_dist(w, BETA) U, tp = 3.4, 0.3 # Matsubara giw_d, giw_o = dimer.gf_met(w_n, 0., tp, 0.5, 0.) giw_d, giw_o, _ = dimer.ipt_dmft_loop(BETA, U, tp, giw_d, giw_o, tau, w_n, 5e-4) g0iw_d, g0iw_o = dimer.self_consistency(1j * w_n, 1j * giw_d.imag, giw_o.real, 0., tp, 0.25) siw_d, siw_o = ipt_imag.dimer_sigma(U, tp, g0iw_d, g0iw_o, tau, w_n) # Continuate sigma with Padé w_set = np.array([0, 3] + list(range(5, 761, 7))) ss, _ = dimer.pade_diag(1j * siw_d.imag, siw_o.real, w_n, w_set, w + 0.0005j) ############################################################################### # Low Energy in Sigma matsubara # ----------------------------- fig, ax = plt.subplots(2, 1, sharex=True)
sd_zew.append(np.polyfit(w_n[:2], siw_d[:2].imag, 1)) so_zew.append(np.polyfit(w_n[:2], siw_o[:2].real, 1)) sd_zew, so_zew = np.array(sd_zew), np.array(so_zew) dw_sig11 = np.ma.masked_array(sd_zew[:, 0], murange >= u_cut) zet = 1 / (1 - dw_sig11.T) tpp = (TP + so_zew[:, 1].T) return zet, tpp tau, w_n = gf.tau_wn_setup(dict(BETA=BETA, N_MATSUBARA=2**12)) # TP 0.3 TP = 0.3 giw_d, giw_o = dimer.gf_met(w_n, 0., TP, 0.5, 0.) murange03 = np.array(sorted(list(np.arange(2.3, 3.46, .1)) + [3.46, 3.47])) zet03, tpp03 = zero_f_meas(giw_d, giw_o, murange03, TP, 3.47) plt.plot(murange03, zet03, '-', lw=2, label=r'$Z$') plt.show() # TP 0.5 TP = 0.5 murange05 = np.array( sorted( list(np.arange(1.2, 2.35, .1)) + list(np.arange(2.327, 2.33, 0.00051)))) zet05, tpp05 = zero_f_meas(giw_d, giw_o, murange05, TP, 3.47) plt.plot(murange05, zet05, '-', lw=2, label=r'$Z$') plt.plot(murange05, np.abs(zet05 * (1 - tpp05)), '*-', lw=2, label=r'$|\eta|$')
def dmft_loop_pm(simulation): """Implementation of the solver""" setup = { 't': 0.5, 'BANDS': 1, 'SITES': 2, } if simulation['new_seed']: if comm.rank == 0: hf.set_new_seed(simulation, ['gtau_d', 'gtau_o']) simulation['U'] = simulation['new_seed'][1] return setup.update(simulation) setup['dtau_mc'] = setup['BETA'] / 2. / setup['N_MATSUBARA'] current_u = 'U' + str(setup['U']) tau, w_n = gf.tau_wn_setup(setup) intm = hf.interaction_matrix(setup['BANDS']) setup['n_tau_mc'] = len(tau) mu, tp, U = setup['MU'], setup['tp'], setup['U'] giw_d_up, giw_o_up = dimer.gf_met(w_n, 1e-3, tp, 0.5, 0.) giw_d_dw, giw_o_dw = dimer.gf_met(w_n, -1e-3, tp, 0.5, 0.) gmix = np.array([[1j * w_n, -tp * np.ones_like(w_n)], [-tp * np.ones_like(w_n), 1j * w_n]]) g0tail = [ np.eye(2).reshape(2, 2, 1), tp * np.array([[0, 1], [1, 0]]).reshape(2, 2, 1), np.array([[tp**2, 0], [0, tp**2]]).reshape(2, 2, 1) ] gtail = [ np.eye(2).reshape(2, 2, 1), tp * np.array([[0, 1], [1, 0]]).reshape(2, 2, 1), np.array([[tp**2 + U**2 / 4, 0], [0, tp**2 + U**2 / 4]]).reshape(2, 2, 1) ] giw_up = np.array([[giw_d_up, giw_o_up], [giw_o_dw, giw_d_dw]]) giw_dw = np.array([[giw_d_dw, giw_o_dw], [giw_o_up, giw_d_up]]) try: # try reloading data from disk with h5.File(setup['ofile'].format(**setup), 'r') as last_run: last_loop = len(last_run[current_u].keys()) last_it = 'it{:03}'.format(last_loop - 1) giw_d, giw_o = pd.get_giw(last_run[current_u], last_it, tau, w_n) except (IOError, KeyError): # if no data clean start last_loop = 0 V_field = hf.ising_v(setup['dtau_mc'], setup['U'], L=setup['SITES'] * setup['n_tau_mc'], polar=setup['spin_polarization']) for loop_count in range(last_loop, last_loop + setup['Niter']): # For saving in the h5 file dest_group = current_u + '/it{:03}/'.format(loop_count) setup['group'] = dest_group if comm.rank == 0: print('On loop', loop_count, 'beta', setup['BETA'], 'U', U, 'tp', tp) # Bethe lattice bath g0iw_up = mat_2_inv(gmix - 0.25 * giw_up) g0iw_dw = mat_2_inv(gmix - 0.25 * giw_dw) g0tau_up = gf.gw_invfouriertrans(g0iw_up, tau, w_n, g0tail) g0tau_dw = gf.gw_invfouriertrans(g0iw_dw, tau, w_n, g0tail) # Impurity solver gtu, gtd = hf.imp_solver([g0tau_up, g0tau_dw], V_field, intm, setup) giw_up = gf.gt_fouriertrans(-gtu, tau, w_n, gtail) giw_dw = gf.gt_fouriertrans(-gtd, tau, w_n, gtail) # Save output if comm.rank == 0: with h5.File(setup['ofile'].format(**setup), 'a') as store: store[dest_group + 'gtau_u'] = gtu store[dest_group + 'gtau_d'] = gtd h5.add_attributes(store[dest_group], setup) sys.stdout.flush()
import matplotlib.pyplot as plt import dmft.common as gf import dmft.dimer as dimer ###################################################################### # Real frequency spectral function # ================================ w = 1e-3j + np.linspace(-4, 4, 2**10) mu, t = 0, 0.5 t2 = t**2 plt.figure() for tab in [0, 0.25, 0.5, 0.75, 1.1]: Gd, Gc = dimer.gf_met(-1j * w, mu, tab, t, 0.) Gd, Gc = dimer.self_consistency(w, Gd, Gc, mu, tab, t2) plt.plot(w.real, -Gd.imag / np.pi, label=r'$t_c={}$'.format(tab)) # plt.plot(w.real, Gd.real, label=r'$\Re e Gd$') # plt.plot(w.real, Gc.real, label=r'$\Re e Gc$') # plt.plot(w.real, Gc.imag, label=r'$\Im m Gc$') plt.legend(loc=0) plt.xlabel(r'$\omega$') plt.ylabel(r'$A(\omega)$') ###################################################################### # Matsubara frequency Green's function # ====================================