Пример #1
0
def averageGreen(delta0, mu0, w, SelfEnergy, parms, Nd, Ntot, tuneup, extra):
    BETA     = float(parms["BETA"]);
    N_LAYERS = int(parms['N_LAYERS']); FLAVORS = int(parms['FLAVORS']); SPINS = int(parms['SPINS']);
    rot_mat = extra['rot_mat'];
    
    # calculate intersite Coulomb energy here
    Vc = zeros(N_LAYERS, dtype = 'f8');

    # convert self energy to the C++ form
    SelfEnergy_rot = array([functions.irotate(SelfEnergy[s], extra['rot_mat']) for s in range(SPINS)]);
    SE = [array([s.flatten() for s in SelfEnergy_rot[n]]) for n in range(SPINS)];

    v_delta = empty(0, 'f8');
    v_nd    = empty(0, 'f8');
    ddelta = 0.; delta_step = 1.;
    dmu = 0.; mu_step = 5; 
    tol = 0.005;
    # Delta loop
    while True:
        delta = delta0 + ddelta;

        v_mu = empty(0, 'f8');
        v_n = empty(0, 'f8');
        # mu loop
        while True:
            mu = mu0 + dmu;
            
            Gavg = average_green.integrate(w, delta, mu, SE, parms, extra);
            Gavg_diag = array([Gavg[0, :, i, i] for i in range(int(parms['NORB']))]).T;
            nf = getDensity(Gavg_diag, parms); 
            my_ntot = 2*sum(nf); # factor of 2 due to spin
    
            if tuneup: print "   adjust mu: " + str(mu) + " " + str(dmu) + " " + str(my_ntot);
            if Ntot < 0 or abs(Ntot - my_ntot) < tol or not tuneup: break;
     
            v_mu = r_[v_mu, dmu];
            v_n = r_[v_n, my_ntot];
            if v_n.min() < Ntot and v_n.max() > Ntot: dmu = interp_root(v_mu, v_n, Ntot);
            else: dmu += (1. if my_ntot < Ntot else -1.)*mu_step;
           
        my_nd = 2*sum(nf[:N_LAYERS*FLAVORS]);

        if tuneup: print "adjust double counting: " + str(delta) + " " + str(ddelta) + " " + str(my_nd) + " " + str(my_nd/N_LAYERS);
        if Nd < 0 or abs(Nd - my_nd) < tol or not tuneup: break;

        v_delta = r_[v_delta, ddelta];
        v_nd = r_[v_nd, my_nd];
        if v_nd.min() < Nd and v_nd.max() > Nd: ddelta = interp_root(v_delta, v_nd, Nd);
        else: ddelta += (1. if my_nd < Nd else -1.)*delta_step;

    Gavg = array([functions.rotate_all(Gavg[s], rot_mat) for s in range(SPINS)]);
    return Gavg, delta, mu, Vc;
from int_2dhopping import *
from numpy import *
from share_fun import grule
from functions import rotate_all

nflavors = 3

nbin = 500
emin = -6.
emax = 6.
broadening = 0.05

mu = 0.
double_counting = 0.        # unused in models containing only correlated orbitals

magnetic_field  = 0.0
numk = 100
bp, wf = grule(numk)        # the Gaussian points and weights

w = linspace(emin, emax, nbin) + 1j*broadening
self_energy = zeros((nbin, 1, nflavors, nflavors), dtype = complex)
self_energy = array([s.flatten() for s in self_energy], dtype = complex)
tight_binding_parameters = array([1.,0.3])

Gavg = calc_Gavg(w, double_counting, mu, self_energy, tight_binding_parameters, 
                 magnetic_field, bp, wf, 0).reshape(nbin, nflavors, nflavors)
G = rotate_all(Gavg, [matrix(eye(nflavors))])
dos = -1/pi*G.imag
savetxt('dos_tight_binding.out', c_[w.real, dos], fmt='%.6f')
SelfEnergy_rot = array([irotate(SelfEnergy[s], rot_mat)
                        for s in range(SPINS)])
SE = array([array([s.flatten() for s in SelfEnergy_rot[n]])
            for n in range(SPINS)])

# prepare the parameter dict
parms = {
        'H' : magnetic_field,
        'N_LAYERS' : N_LAYERS,
        'FLAVORS' : FLAVORS,
        'SPINS' : SPINS,
        'NORB' : NORB,
        'INTEGRATE_MOD' : 'int_donly_tilted_3bands',
        'np' : num_processes,
        }

extra = {
        'HR' : HR,
        'R' : R,
        'GaussianData' : grule(numk),
        }

# calculate the k-integral
Gavg = average_green.integrate(w+1j*broadening, double_counting, mu, SE,
                               parms, extra, parallel)
Gavg = array([rotate_all(Gavg[s], rot_mat, need_extra = True) for s in range(SPINS)])

dos = -1/pi*Gavg[0].imag 
savetxt('dos_dft_mlwf.mpi', c_[w, dos], fmt='%.6f')

Пример #4
0
def averageGreen(delta0, mu0, w, SelfEnergy, parms, Nd, Ntot, tuneup, extra):
    N_LAYERS = int(parms['N_LAYERS'])
    FLAVORS = int(parms['FLAVORS'])
    SPINS = int(parms['SPINS'])
    rot_mat = extra['rot_mat']
    parallel = int(parms.get('KINT_PARALLEL', 2))
    
    # calculate intersite Coulomb energy here
    Vc = zeros(N_LAYERS, dtype=float)

    # convert self energy to the C++ form
    SelfEnergy_rot = array([irotate(SelfEnergy[s], rot_mat)
                           for s in range(SPINS)])
    SE = array([array([s.flatten() for s in SelfEnergy_rot[n]])
                for n in range(SPINS)])

    v_delta = array([])
    ddelta = 0.
    delta_step = 1.
    v_nd = array([])
    dmu = 0.
    mu_step = 0.5

    tol = 0.003
    firsttime = True
    initial_Gasymp = extra['G_asymp_coefs'] if 'G_asymp_coefs' in extra.keys()\
                     else None
    starting_error = 0.
    # Delta loop
    while True:
        delta = delta0 + ddelta
        if initial_Gasymp is not None:
            extra['G_asymp_coefs'][:N_LAYERS*FLAVORS] = initial_Gasymp[:N_LAYERS*FLAVORS] - ddelta
        v_mu = array([]) 
        v_n = array([])

        # mu loop
        while True:
            mu = mu0 + dmu
            if initial_Gasymp is not None:
                extra['G_asymp_coefs'] = initial_Gasymp - dmu
            
            Gavg = integrate(w, delta, mu, SE, parms, extra, parallel)
            Gavg_diag = array([[diag(Gavg[s, n]) for n in range(size(Gavg,1))]
                               for s in range(SPINS)])
            nf = getDensityFromGmat(Gavg_diag, float(parms['BETA']), extra)
            my_ntot = sum(nf) if SPINS == 2 else 2*sum(nf)

            print "   adjust mu: %.5f  %.5f  %.5f"%(mu, dmu, my_ntot)
            if firsttime:
                starting_error = abs(Ntot - my_ntot)/N_LAYERS
                Gavg0 = Gavg.copy()
                firsttime = False
            if Ntot < 0 or abs(Ntot - my_ntot)/N_LAYERS < tol or not tuneup:
                break
    
            v_mu = r_[v_mu, dmu]
            v_n = r_[v_n, my_ntot]
            if v_n.min() < Ntot and v_n.max() > Ntot:
                dmu = interp_root(v_mu, v_n, Ntot)
            else:
                dmu += (1. if my_ntot < Ntot else -1.)*mu_step

        my_nd = sum(nf[:, :N_LAYERS*FLAVORS])
        if tuneup:
            print ('adjust double counting: %.5f  %.5f  '
                   '%.5f  %.5f')%(delta, ddelta, my_nd, my_nd/N_LAYERS)
        if Nd < 0 or abs(Nd - my_nd)/N_LAYERS < tol or not tuneup:
            break

        v_delta = r_[v_delta, ddelta]
        v_nd = r_[v_nd, my_nd]
        if v_nd.min() < Nd and v_nd.max() > Nd:
            ddelta = interp_root(v_delta, v_nd, Nd)
        else:
            ddelta += (1. if my_nd < Nd else -1.)*delta_step

    # adjusted Gavg with mu_new = mu_0 + N*dmu and
    # delta_new = delta_0 + N*ddelta;
    N = float(parms.get('TUNEUP_FACTOR', 1))
    if N != 1. and (ddelta != 0. or dmu != 0.) and starting_error < 50*tol:
        mu = mu0 + N*dmu
        delta = delta0 + N*ddelta
        Gavg = integrate(w, delta, mu, SE, parms, extra, parallel)
        print ('TUNEUP_FACTOR = %d final adjustment: mu = %.4f, dmu = %.4f, '
               'delta = %.4f, ddelta = %.4f')%(N, mu, N*dmu, delta, N*ddelta)

    Gavg = array([rotate_all(Gavg[s], rot_mat) for s in range(SPINS)])
    Gavg0 = array([rotate_all(Gavg0[s], rot_mat, need_extra = True)
                   for s in range(SPINS)])
    if initial_Gasymp is not None:
        extra['G_asymp_coefs'] = initial_Gasymp
    return Gavg, Gavg0, delta, mu, Vc