#!/usr/bin/env python # coding: utf-8 # # Reproduce: Dielectric function, screening, and plasmons in two-dimensional graphene # E. H. Hwang and S. Das Sarma, Dielectric function, screening, and plasmons in two-dimensional graphene, Phys. Rev. B 75, 205418 (2007). # Reproduced by Eunjong Kim (ekim7206@gmail.com) # In[1]: from numpy import * from scipy.integrate import dblquad from scipy.optimize import newton import matplotlib import matplotlib.pyplot as plt # In[2]: import warnings warnings.filterwarnings("ignore") # In[3]: get_ipython().run_line_magic('matplotlib', 'inline') # matplotlib setup matplotlib.rcParams['font.size'] = 18 matplotlib.rcParams['text.usetex'] = True # Unlike conventional 2D systems with quadratic dispersion, the graphene shows a linear energy-momentum relation # $$\varepsilon_{\mathbf{k}s} = s\hbar v_\mathrm{F} |\mathbf{k}| $$ # near the $K, K'$ points of the Brillouin zone. Here, $v_\mathrm{F}$ is the 2D Fermi velocity and $s=\pm1$ is the band index. Based on this linear relation, the dynamical screening function (dielectric function) can be obtained using the random-phase approximation (RPA): # $$\epsilon^\mathrm{RPA}(\mathbf{q},\omega) = 1 - v_\mathrm{C}(\mathbf{q})\chi_0(\mathbf{q},\omega)$$ # where $v_\mathrm{C}(\mathbf{q}) = 2\pi e^2/\kappa q$ is the 2D Coulomb potential in the momentum space. # In[4]: def energy(k, phi, q, s): ''' Linear energy dispersion near the K point of the momentum space ''' return (s * sqrt(k ** 2 + q ** 2 + 2 * k * q * cos(phi))) # In[5]: q_e = 1.60217662e-19 * 2.9979245800e9 # charge of an electron in units of Coulomb kappa = 2.5 def v_c(q): ''' Coulomb potential in momentum space in Gaussian units (CGS) ''' return 2 * pi * q_e ** 2 / (kappa * abs(q)) # $\chi_0 (\mathbf{q},\omega)$ is the non-interacting density-density response function given by # $$\chi_0(\mathbf{q},\omega) = g_s g_v\sum_{s,s' = \pm 1} \int \frac{d^2 k}{(2\pi)^2} \frac{f_{\mathbf{k},s} - f_{\mathbf{k+q},s'}}{\hbar \omega + \varepsilon_{\mathbf{k},s} - \varepsilon_{\mathbf{k+q},s'}+i\eta} F_{s, s'}(\mathbf{k},\mathbf{k+q}),$$ # where $g_s=g_v=2$ denote the spin and valley degeneracies and $\eta\rightarrow 0^+$ is an infinitesimal positive number. $F_{s,s'}(\mathbf{k},\mathbf{k}')= (1 + ss'\cos{\theta_{\mathbf{k},\mathbf{k}'}})/2$ is the overlap between wavefunctions with $\theta_{\mathbf{k},\mathbf{k}'}$ being the angle between vectors $\mathbf{k}$ and $\mathbf{k}'$. Here, $f_{\mathbf{k}, s}$ is the Fermi distribution function. # The non-interacting density-density response function $\chi_0$ can be decomposed into two parts, $\chi_0 = \chi^{+}_0 + \chi^{-}_0$, with # $$\chi^{+}_0(\mathbf{q}, \omega) = \frac{g_s g_v}{2} \int \frac{d^{2}k}{(2\pi)^2}\left[\frac{(f_{\mathbf{k},+} - f_{\mathbf{k+q},+})(1 + \cos{\theta_{\mathbf{k},\mathbf{k+q}}})}{\hbar\omega + \varepsilon_{\mathbf{k},+}-\varepsilon_{\mathbf{k+q},+} + i\eta} # +\frac{f_{\mathbf{k},+} (1 - \cos{\theta_{\mathbf{k},\mathbf{k+q}}})}{\hbar\omega + \varepsilon_{\mathbf{k},+}-\varepsilon_{\mathbf{k+q},-} + i\eta} # -\frac{f_{\mathbf{k+q},+}(1 - \cos{\theta_{\mathbf{k},\mathbf{k+q}}})}{\hbar\omega + \varepsilon_{\mathbf{k},-}-\varepsilon_{\mathbf{k+q},+} + i\eta}\right],$$ # $$\chi^{-}_0(\mathbf{q}, \omega) = \frac{g_s g_v}{2} \int \frac{d^{2}k}{(2\pi)^2}\left[\frac{(f_{\mathbf{k},-} - f_{\mathbf{k+q},-})(1 + \cos{\theta_{\mathbf{k},\mathbf{k+q}}})}{\hbar\omega + \varepsilon_{\mathbf{k},-}-\varepsilon_{\mathbf{k+q},-} + i\eta} # +\frac{f_{\mathbf{k},-} (1 - \cos{\theta_{\mathbf{k},\mathbf{k+q}}})}{\hbar\omega + \varepsilon_{\mathbf{k},-}-\varepsilon_{\mathbf{k+q},+} + i\eta} # -\frac{f_{\mathbf{k+q},-}(1 - \cos{\theta_{\mathbf{k},\mathbf{k+q}}})}{\hbar\omega + \varepsilon_{\mathbf{k},+}-\varepsilon_{\mathbf{k+q},-} + i\eta}\right].$$ # $$\cos{\theta_{\mathbf{k},\mathbf{k+q}}} = \frac{\mathbf{k}\cdot\mathbf{k+q}}{k|\mathbf{k+q}|} = \frac{k + q\cos{\phi}}{\sqrt{k^2 + q^2 + 2kq\cos{\phi}}}$$ # In[6]: def cosine(k, phi, q): ''' cosine between the two vectors k and k + q as a function of phi, which is the angle bewteen k and q. ''' return ((k + q * cos(phi)) / sqrt(k**2 + q**2 + 2 * k * q * cos(phi))) # In the zero-temperature limit $T\rightarrow 0$, the Fermi distribution function $f_{\mathbf{k} s}$ reduces to a simple step function or unity depending on the band index $s=\pm 1$: # $$f_{\mathbf{k} s} = \left[e^{\beta(\varepsilon_{\mathbf{k}s}-\mu)} + 1\right]^{-1}\quad \xrightarrow{T\rightarrow 0} \quad \Theta(\varepsilon_\mathrm{F} - \varepsilon_{\mathbf{k}s}) = # \begin{cases} \Theta(k_\mathrm{F} - k) & \textrm{for }s= +1 \\ # 1 & \textrm{for }s=-1 # \end{cases}$$ # Here, the Fermi energy is defined as $\varepsilon_\mathrm{F} = \hbar v_\mathrm{F}k_\mathrm{F}$, with $k_\mathrm{F}$ being the Fermi wavevector. # In[7]: eta = 1e-4 # We express the plus and the minus polarizabilities in simpler forms and perform the numerical integration: # $$\therefore \frac{\chi^{+}_0(\mathbf{q},\omega)}{D(\varepsilon_\mathrm{F})} = \int_{\tilde{k}<1} \frac{d^{2}\tilde{k}}{4\pi}\left[\left(\frac{1 + \cos{\theta_{\mathbf{k},\mathbf{k+q}}}}{\tilde{\omega} + \tilde{\varepsilon}_{\mathbf{k},+}-\tilde{\varepsilon}_{\mathbf{k+q},+} + i\tilde{\eta}} # +\frac{1 - \cos{\theta_{\mathbf{k},\mathbf{k+q}}}}{\tilde{\omega} + \tilde{\varepsilon}_{\mathbf{k},+}-\tilde{\varepsilon}_{\mathbf{k+q},-} + i\tilde{\eta}} # \right) # - # \left(\frac{1 + \cos{\theta_{\mathbf{k-q},\mathbf{k}}}}{\tilde{\omega} + \tilde{\varepsilon}_{\mathbf{k-q},+}-\tilde{\varepsilon}_{\mathbf{k},+} + i\tilde{\eta}} + # \frac{1 - \cos{\theta_{\mathbf{k-q},\mathbf{k}}}}{\tilde{\omega} + \tilde{\varepsilon}_{\mathbf{k-q},-}-\tilde{\varepsilon}_{\mathbf{k},+} + i\tilde{\eta}} \right) # \right] $$ # In[8]: def polarizability0_p_integrand(k, phi, q, omega): ''' For the evaluation of this dblquad, k-integration followed by phi-integration is more efficient. ''' e11 = (1 + cosine(k, phi, q)) / (omega + energy(k, phi, 0, +1) - energy(k, phi, q, +1) + 1j * eta) e12 = (1 - cosine(k, phi, q)) / (omega + energy(k, phi, 0, +1) - energy(k, phi, q, -1) + 1j * eta) e1 = e11 + e12 e21 = (1 + cosine(k, pi + phi, q)) / (omega + energy(k, pi + phi, q, +1) - energy(k, phi, 0, +1) + 1j * eta) e22 = (1 - cosine(k, pi + phi, q)) / (omega + energy(k, pi + phi, q, -1) - energy(k, phi, 0, +1) + 1j * eta) e2 = - (e21 + e22) return - k * (e1 + e2) / (4 * pi) def polarizability0_p_real(q, omega): return dblquad(lambda k, phi: polarizability0_p_integrand(k, phi, q, omega).real, 0, 2 * pi, lambda k: 0, lambda k: 1, epsabs=1e-05, epsrel=1e-05)[0] def polarizability0_p_imag(q, omega): return dblquad(lambda k, phi: polarizability0_p_integrand(k, phi, q, omega).imag, 0, 2 * pi, lambda k: 0, lambda k: 1, epsabs=1e-05, epsrel=1e-05)[0] # $$\chi^{-}_0(\mathbf{q}, \omega) \xrightarrow{T\rightarrow0} \frac{g_s g_v}{2} \int \frac{d^{2}k}{(2\pi)^2}\left[ # \frac{ 1}{\hbar\omega + \varepsilon_{\mathbf{k},-}-\varepsilon_{\mathbf{k+q},+} + i\eta} # -\frac{1}{\hbar\omega + \varepsilon_{\mathbf{k},+}-\varepsilon_{\mathbf{k+q},-} + i\eta}\right](1 - \cos{\theta_{\mathbf{k},\mathbf{k+q}}}) $$ # $$\therefore \frac{\chi^{-}_0(\mathbf{q}, \omega)}{D(\varepsilon_\mathrm{F})}= \int \frac{ d^{2}\tilde{k}}{4\pi}\left[ # \frac{1}{\tilde{\omega} + \tilde{\varepsilon}_{\mathbf{k},-}-\tilde{\varepsilon}_{\mathbf{k+q},+} + i\tilde{\eta}} # -\frac{1}{\tilde{\omega} + \tilde{\varepsilon}_{\mathbf{k},+}-\tilde{\varepsilon}_{\mathbf{k+q},-} + i\tilde{\eta}}\right](1 - \cos{\theta_{\mathbf{k},\mathbf{k+q}}}) $$ # where $\tilde{\omega} = \hbar\omega/\varepsilon_\mathrm{F}$, $\tilde{\varepsilon}_{\mathbf{k},s} = \varepsilon_{\mathbf{k},s}/\varepsilon_\mathrm{F}$, and $\tilde{k} = k/k_\mathrm{F}$. Here $$D(\varepsilon_\mathrm{F}) = \frac{g_s g_v}{2\pi} \frac{k_\mathrm{F}}{\hbar v_\mathrm{F}} = \frac{g_s g_v}{2\pi}\frac{k_\mathrm{F}}{\varepsilon_\mathrm{F}}$$ # is the density of states at the Fermi energy. Note that the static polarizability at $q=0$ satisfies $$\Pi_0(0, 0) = \Pi_0^{+}(0,0) + \Pi_0^{-} (0, 0) = D(\varepsilon_\mathrm{F}).$$ # In[9]: # spin and valley degeneracies g_s, g_v = 2, 2 # density in units of cm^{-2} n = 1e12 # Fermi wavevector in CGS units wavevector_F = (4 * pi * n / (g_s * g_v))**(1/2) hbar = 1.0545716e-27 # Fermi energy in CGS units energy_F = 6.5 * 1.60217662e-12 * 1e-8 # Density of states at the Fermi level in CGS units DOS_F = g_s * g_v * wavevector_F / (2 * pi * energy_F) # In[10]: def polarizability0_m_integrand(k, phi, q, omega): ''' For the evaluation of this dblquad, phi-integration followed by k-integration is much more efficient. ''' e1 = + 1 / (omega + energy(k, phi, 0, -1) - energy(k, phi, q, +1) + 1j * eta) e2 = - 1 / (omega + energy(k, phi, 0, +1) - energy(k, phi, q, -1) + 1j * eta) e = (e1 + e2) * (1 - cosine(k, phi, q)) return - k * e / (4 * pi) k_c = 50 # cutoff wavevector for numerical integration def polarizability0_m_real(q, omega): return dblquad(lambda phi, k: polarizability0_m_integrand(k, phi, q, omega).real, 0, k_c, lambda phi: 0, lambda phi: 2 * pi, epsabs=1e-05, epsrel=1e-05)[0] def polarizability0_m_imag(q, omega): return dblquad(lambda phi, k: polarizability0_m_integrand(k, phi, q, omega).imag, 0, k_c, lambda phi: 0, lambda phi: 2 * pi, epsabs=1e-05, epsrel=1e-05)[0] # In[11]: def polarizability0_real(q, omega): return (polarizability0_p_real(q, omega) + polarizability0_m_real(q, omega)) def polarizability0_imag(q, omega): return (polarizability0_p_imag(q, omega) + polarizability0_m_imag(q, omega)) def polarizability0(q, omega): return (polarizability0_real(q, omega) + 1j * polarizability0_imag(q, omega)) # The interacting polarizability $\Pi^\mathrm{RPA}(\mathbf{q},\omega)$ within RPA is calculated as follows: # $$ \Pi^\mathrm{RPA}(\mathbf{q},\omega) = \frac{\Pi_0(\mathbf{q},\omega)}{\epsilon^\mathrm{RPA}(\mathbf{q},\omega)}=\frac{\Pi_0(\mathbf{q},\omega)}{1 - v_\mathrm{C}(\mathbf{q})\Pi_0(\mathbf{q},\omega)}$$ # The loss function is given by # $$ -\mathrm{Im}\left[\frac{1}{\epsilon^\mathrm{RPA}(\mathbf{q},\omega)}\right] = -\mathrm{Im}\left[1 + v_\mathrm{C}(\mathbf{q})\Pi^\mathrm{RPA} (\mathbf{q},\omega) \right] = -\mathrm{Im}\left[\frac{1}{1-v_\mathrm{C}(\mathbf{q})\Pi_0(\mathbf{q},\omega)}\right]$$ # ## Plasmon mode dispersion $\omega(\mathbf{q})$ in 2D graphene # In[64]: N = 20 # range of omega/E_F values: 0 to 3 omega = linspace(1e-2, 3, N) # range of q/k_F values: 0 to 3 q = linspace(1e-2, 3, N) # In[13]: omega0 = sqrt(g_s * g_v * q_e ** 2 * energy_F / (2 * kappa)) # In[14]: # empty array to store the imaginary part of polarizability values polarizability = zeros((N, N), dtype=complex) # In[15]: # time-consuming calculation for idx1, q_ in enumerate(q): for idx2, omega_ in enumerate(omega): polarizability0_ = polarizability0(q_, omega_) polarizability[idx1, idx2] = (polarizability0_ / (1 - v_c(q_ * wavevector_F) * DOS_F * polarizability0_)) print(r"idx1 = %d, q = %f complete" % (idx1, q_)) # In[16]: # plasmon dispersion (numerical) --- needs revision # plasmon_freq = zeros(N) #for idx, q_ in enumerate(q): # plasmon_freq[idx] = newton(lambda omega: (1 - v_c(q_ * wavevector_F) * DOS_F * # polarizability0_real(q_,omega)), # omega0 * sqrt(q_) / energy_F, tol=1e-4) # print(plasmon_freq[idx]) # In[65]: fig, ax = plt.subplots(1,1, figsize=(5.5,5)) #ax.plot(q, plasmon_freq) ax.plot(q, omega0 * sqrt(q)/ energy_F, ls='--', color='black', lw=2, label=r'$\omega = \omega_0 \sqrt{q}$') ax.set_xlim([0, 3]); ax.set_ylim([0, 3]); #ax.imshow(q, omega, polarizability_imag, origin='down') cs = ax.contourf(q, omega, polarizability.imag.T, [0.001, 0.1, 0.2, 0.3, 0.4]) ax.set_xlabel(r'$q/k_\mathrm{F}$') ax.set_ylabel(r'$\omega/\varepsilon_\mathrm{F}$') fig.colorbar(cs, ax=ax) # The imaginary part of the dielectric function $\epsilon^{\mathrm{RPA}}(\mathbf{q},\omega)$ calculated numerically within RPA is mapped. To find the plasmon dispersion, # ## Static Polarizabililty ($\omega=0$) for 2D graphene # In[68]: N = 20 # range of q/k_F values: 0 to 5 q = linspace(1e-2, 5, N) # In[57]: # empty arrays to store polarizability values polarizability0_p, polarizability0_m = zeros(N), zeros(N) # In[58]: # static polarizability for idx, q_ in enumerate(q): polarizability0_p[idx] = polarizability0_p_real(q_, 0) polarizability0_m[idx] = polarizability0_m_real(q_, 0) # In[69]: fig, ax = plt.subplots(1,1, figsize=(5,5)) ax.plot(q, polarizability0_p, label=r'$\Pi^{+}_0$', lw=2) ax.plot(q, polarizability0_m, label=r'$\Pi^{-}_0$', lw=2) ax.plot(q, polarizability0_p + polarizability0_m, label=r'$\Pi_0$', lw=2) ax.set_xlabel(r'$q/k_\mathrm{F}$') ax.set_ylabel(r'$\Pi_0(q,\omega=0)/D(\varepsilon_\mathrm{F})$') fig.text(0.12, 0.93, r'Static polarizability for 2D graphene') ax.set_xlim([0, 5]); ax.set_ylim([0, 2]) ax.legend(loc=0); # This is the static $(\omega=0)$ polarizability for 2D graphene and Figure 2 of [Phys. Rev. B 75, 205418 (2007)] has been reproduced. # # Version Information # In[13]: get_ipython().run_line_magic('reload_ext', 'version_information') get_ipython().run_line_magic('version_information', 'numpy, scipy, matplotlib')