python wannier90 基于wannier90的*_hr.dat文件选取截断hopping绘制能带图

news/2024/12/4 20:50:28/

        我们知道wannier90可以根据选取TMDs的轨道信息生成详细的hopping energy *_hr.dat文件,选取所有的hopping绘制起来的时候比较简单,但是我们发现取几圈的近似hopping也可以将band表示出来,类似的思想有Pybinding的三带近似(DOI: 10.1103/PhysRevB.88.085433)和Fang的TMDs的紧束缚模型半经验参数近似(DOI: 10.1103/PhysRevB.92.205108)等等。

        我们首先要知道wannier90.dat文件里的数据格式,我们需要的是 类似于

-12   -6    0    1    1    0.000020   -0.000000
-12   -6    0    2    1    0.000000   -0.000000
-12   -6    0    3    1    0.000000    0.000000
-12   -6    0    4    1    0.000004    0.000000
-12   -6    0    5    1    0.000000    0.000000

这样的数据,这里前面三个代表directions[x,y,z] 中间两个代表[fromAtom, toAtom]也就是Rij,后面两个值代表了hopping,代表复数 a+bi 的[a, b]。

        这里的画圈有点类似,也就是根据选择当前原子和目标原子的距离来简要进行阶段,例如下图展示了四层原子(包括[0,0]),可能第三圈的hopping贡献远大于第四圈,所以截取到第三圈即可绘制band。

 这里给出MX_2部分示例,选取M的d_(z^2) d_(xy) d_(x^2-y^2)和总的S轨道计算的一个wannier90 *_hr.dat文件,任意选择截取1-10([0,0]就算了几乎是onsite energy)圈的一个代码,其实取到第5圈就已经比较近似于全部圈层的结果了:

#!/usr/bin python
# -*- encoding: utf-8 -*-
'''
@Author  :   Celeste Young
@File    :   基于fang2015提取MoS2轨道.py    
@Time    :   2023/4/3 14:47  
@E-mail  :   iamwxyoung@qq.com
@Tips    :   
'''import time
import matplotlib.pyplot as plt
import pandas as pd
# import pybinding as pb
import numpy as np
import functools
import threadingdef make_path(k0, k1, *ks, step=0.1):  # kpath k_points = [np.atleast_1d(k) for k in (k0, k1) + ks]if not all(k.shape == k_points[0].shape for k in k_points[:1]):raise RuntimeError("All k-points must have the same shape")k_paths = []point_indices = [0]for k_start, k_end in zip(k_points[:-1], k_points[1:]):num_steps = int(np.linalg.norm(k_end - k_start) // step)# k_path.shape == num_steps, k_space_dimensionsk_path = np.array([np.linspace(s, e, num_steps, endpoint=False)for s, e in zip(k_start, k_end)]).Tk_paths.append(k_path)point_indices.append(point_indices[-1] + num_steps)k_paths.append(k_points[-1])return np.vstack(k_paths)  # , point_indices)def isinDirect(v_, hvts):  # 判断是否在所选的directions里,上图的n层for vs in hvts:if ''.join(v_) == ''.join(list(map(str, vs))):return Truereturn Falsedef read_dat(*args, **kwargs):with open("data/wannier90_hr_MoS2.dat", "r") as f:lines = f.readlines()rij = [[[] for col in range(nb)] for row in range(nb)]tij = [[[] for col in range(nb)] for row in range(nb)]for line in lines:ll = line.split()if isinDirect(ll[:3], kwargs['hvts']):x, y, z, frAt, toAt = list(map(int, ll[:5]))t_real, t_image = list(map(float, ll[5:]))rij[frAt - 1][toAt - 1].append([x, y, z])tij[frAt - 1][toAt - 1].append([t_real + 1j * t_image])return rij, tijdef plot_rec(*args, **kwargs):  # 绘制布里渊区的积分路径fig = plt.figure(figsize=(5, 5))ax = plt.axes()ax.arrow(0, 0, a1[0], a1[1], length_includes_head=False, head_width=0.05, fc='b', ec='k')ax.arrow(0, 0, a2[0], a2[1], length_includes_head=False, head_width=0.05, fc='b', ec='k')ax.arrow(0, 0, b1[0], b1[1], length_includes_head=False, head_width=0.05, fc='r', ec='red')ax.arrow(0, 0, b2[0], b2[1], length_includes_head=False, head_width=0.05, fc='r', ec='red')ax.plot([0, Middle[0], K1[0], 0], [0, Middle[1], K1[1], 0])ax.scatter([0, Middle[0], K1[0], 0], [0, Middle[1], K1[1], 0])ax.set_xlim(-1, 4)ax.set_ylim(-2, 4)ax.grid()plt.show()def phase(*args, **kwargs):rij = kwargs['hr']wk = kwargs['wk']R_vec = 0for ii in range(3):R_vec += rij[ii] * basis_vector[ii]inner_product = np.dot(R_vec, wk)return np.exp(1j * inner_product)def Hamham(wak, tij, rij):h = np.zeros((nb, nb), dtype=complex)for ii in range(nb):for jj in range(nb):for vij in range(len(rij[ii][jj])):hr = rij[ii][jj][vij]h[ii, jj] = h[ii, jj] + tij[ii][jj][vij][0] * phase(hr=hr, wk=wak)return hdef get_sphere(*args, **kwargs):  #获取需要的层的directions,传入参数n=[1,11)sp_ = args[0]spDict = {}# sp = 0sp0 = [[0, 0, 0]]spDict['sp0'] = sp0# sp = 1 >> 3*2sp1 = [[1, 0, 0], [1, 1, 0], [0, 1, 0]]sp1 = sp1 + [list(-np.array(sp1[i])) for i in range(len(sp1))]spDict['sp1'] = sp1# sp = 2 >> 3*2sp2 = [[2, 1, 0], [1, 2, 0], [-1, 1, 0]]sp2 = sp2 + [list(-np.array(sp2[i])) for i in range(len(sp2))]spDict['sp2'] = sp2# sp = 3 >> 3*2sp3 = [[2, 0, 0], [2, 2, 0], [0, 2, 0]]sp3 = sp3 + [list(-np.array(sp3[i])) for i in range(len(sp3))]spDict['sp3'] = sp3# sp = 4 >> 6*2sp4 = [[3, 1, 0], [3, 2, 0], [2, 3, 0], [1, 3, 0], [-1, 2, 0], [-2, 1, 0]]sp4 = sp4 + [list(-np.array(sp4[i])) for i in range(len(sp4))]spDict['sp4'] = sp4# sp = 5 >> 3*2sp5 = [[3, 0, 0], [3, 3, 0], [0, 3, 0]]sp5 = sp5 + [list(-np.array(sp5[i])) for i in range(len(sp5))]spDict['sp5'] = sp5# sp = 6 >> 3*2sp6 = [[4, 2, 0], [2, 4, 0], [-2, 2, 0]]sp6 = sp6 + [list(-np.array(sp6[i])) for i in range(len(sp6))]spDict['sp6'] = sp6# sp = 7 >> 3*2sp7 = [[4, 1, 0], [4, 3, 0], [3, 4, 0], [1, 4, 0], [-1, 3, 0], [-3, 1, 0]]sp7 = sp7 + [list(-np.array(sp7[i])) for i in range(len(sp7))]spDict['sp7'] = sp7# sp = 8 >> 3*2sp8 = [[4, 0, 0], [4, 4, 0], [0, 4, 0]]sp8 = sp8 + [list(-np.array(sp8[i])) for i in range(len(sp8))]spDict['sp8'] = sp8sp9 = [[5, 2, 0], [5, 3, 0], [2, 5, 0], [3, 5, 0], [-2, 3, 0], [-3, 2, 0]]sp9 = sp9 + [list(-np.array(sp9[i])) for i in range(len(sp9))]spDict['sp9'] = sp9sp10 = [[5, 1, 0], [5, 4, 0], [1, 5, 0], [4, 5, 0], [-1, 4, 0], [-4, 1, 0]]sp10 = sp10 + [list(-np.array(sp10[i])) for i in range(len(sp10))]spDict['sp10'] = sp10if sp_ == 0:return sp0tmpl = []for i in range(sp_):tmpl += [j for j in spDict['sp%d' % i]]return tmpldef selectAllOrbital():with open("data/wannier90_hr_MoS2.dat", "r") as f:lines = f.readlines()rij = [[[] for col in range(nb)] for row in range(nb)]tij = [[[] for col in range(nb)] for row in range(nb)]for line in lines:ll = line.split()if len(ll) == 7:x, y, z, frAt, toAt = list(map(int, ll[:5]))t_real, t_image = list(map(float, ll[5:]))rij[frAt - 1][toAt - 1].append([x, y, z])tij[frAt - 1][toAt - 1].append([t_real + 1j * t_image])hamilton = functools.partial(Hamham, tij=tij, rij=rij)idx = 0result = np.zeros([len(path), 11])for kxy in range(len(path)):k = np.r_[path[kxy], [0]]w, t = np.linalg.eig(hamilton(k))w = list(w)w.sort()result[idx, :] = np.real(w)  # 将本征值进行保存idx += 1xk = [0, rt3, rt3 + 1, rt3 + 3]kk = np.linspace(0, 4.7, num=len(path))  # 作为x轴,使其和本征值矩阵每一列的y的值个数相同plt.figure(figsize=(4, 5))plt.plot(kk, result, c="r")plt.xticks(xk, ["Γ", "M", "K", "Γ"])plt.ylabel("Energy(eV)", fontsize=14)plt.axvline(rt3, color='gray', linestyle='--')plt.axvline(rt3 + 1, color='gray', linestyle='--')plt.title('all orbital')plt.savefig('all orbital.png')print('Saved all orbital figure!')def selectOrbital(orbi):print('started %d/%d' % (orbi, 10))hvts = get_sphere(orbi)result = np.zeros([len(path), 11])  # 解的矩阵Rij, Tij = read_dat(hvts=hvts)hamilton = functools.partial(Hamham, tij=Tij, rij=Rij)idx = 0for kxy in range(len(path)):k = np.r_[path[kxy], [0]]w, t = np.linalg.eig(hamilton(k))w = list(w)w.sort()result[idx, :] = np.real(w)  # 将本征值进行保存idx += 1xk = [0, rt3, rt3 + 1, rt3 + 3]kk = np.linspace(0, 4.7, num=len(path))  # 作为x轴,使其和本征值矩阵每一列的y的值个数相同plt.figure(figsize=(4, 5))plt.plot(kk, result, c="r")plt.xticks(xk, ["Γ", "M", "K", "Γ"])plt.ylabel("Energy(eV)", fontsize=14)plt.axvline(rt3, color='gray', linestyle='--')plt.axvline(rt3 + 1, color='gray', linestyle='--')plt.title('%d orbital' % orbi)plt.savefig('%d orbital.png' % orbi)print('finish %d/%d' % (orbi, 10))if __name__ == '__main__':# start heretime1 = time.time()nb = 11  # number of bandsa = 3.160  # 3.18c = 12.29  # distance of layersdxx = 3.13  # distance of orbital X-Xdxm = 2.41  # distance of orbital X-M# constant checkedrt3 = 3 ** 0.5pi = np.pia1 = a * np.array([rt3 / 2, -1 / 2, 0])a2 = a * np.array([0, 1, 0])a3 = a * np.array([0, 0, 5])basis_vector = np.array([a1, a2, a3])b1 = 2 * pi / a * np.array([1 / rt3, 1])b2 = 4 * pi / a / rt3 * np.array([1, 0])Gamma = np.array([0, 0])Middle = 1 / 2 * b1K1 = 1 / 3 * (2 * b1 - b2)K2 = -1 / 3 * (2 * b1 - b2)# plot_rec()path = make_path(Gamma, Middle, K1, Gamma, step=0.01)# selectAllOrbital()  # 这里取消注释会绘制总的圈层的bandfor orb in range(1, 11):selectOrbital(orbi=orb)time2 = time.time()print('>> Finished, use time %d s' % (time2 - time1))

附上我的hr.dat的结果图:


http://www.ppmy.cn/news/44782.html

相关文章

Softing新版HART多路复用器软件支持西门子控制器

用于访问配置和诊断数据的HART多路复用器软件——Softing smartLink SW-HT,现在支持西门子的ET200远程IO和FDT/DTM接口。 smartLink SW-HT是一个基于Docker容器的软件应用。通过该软件,用户可以快速地访问以太网远程IO的HART设备,并且无需额外…

sentiel安装与整合

(1)方案一:超时处理 设定超时时间,请求超过一定时间没有响应就返回错误信息,不会无休止等待(只能缓解,不能从根本上解决) (2)方案二:舱壁模式 限定每个业务能使用的线程数,避免耗尽整个tomcat的资源,因此也叫线程隔离。(会造成资源浪费) (3)方案三:熔断降…

LeetCode 1041. Robot Bounded In Circle【字符串,模拟】中等

本文属于「征服LeetCode」系列文章之一,这一系列正式开始于2021/08/12。由于LeetCode上部分题目有锁,本系列将至少持续到刷完所有无锁题之日为止;由于LeetCode还在不断地创建新题,本系列的终止日期可能是永远。在这一系列刷题文章…

关于yolov7的一些理解

论文: https://arxiv.org/abs/2207.02696 Github: https://github.com/WongKinYiu/yolov7 YOLOV7的一些理解 1.摘要2.创新点3.具体工作3.1.网络结构优化3.2.辅助头训练3.3.标签分配策略3.4.重参数结构3.5.其它 1.摘要 Yolov7是Yolov4团队的作品,受到了yolo原作者…

前段时间面了15个人,发现这些测试人都有个通病......

前段时间面了15个人,怎么说呢,基本上没有符合要求的,其实一开始瞄准的就是中级的水准,也没指望来大牛,提供的薪资在10-20k,面试的人很多,但平均水平很让人失望。看简历很多都是3年工作经验&…

10个前端开发者需要掌握的DOM技巧

Web开发不断发展,掌握最新的趋势和最佳实践对每位开发者来说都至关重要。Web开发的最重要方面之一就是使用文档对象模型(DOM)。这篇文章中,小蓝将与大家共同探讨10个必须掌握的DOM技巧,帮助您成为更高效、更有效的开发…

Stable Diffusion本地搭建windows and linux(附搭建环境)

linux搭建过程以centos为例 1.使用git工具下载项目文件到本地文件夹,命令如下: git clone https://github.com/IDEA-CCNL/stable-diffusion-webui.git然后进入该文件夹: cd stable-diffusion-webui2.运行自动化脚本 运行webui.sh安装一些p…

Linux初学(CnetOS7 Linux)之切换命令模式

通常我们也称命令模式为终端机接口,terminal 或 console 。 Linux 预设的情况下会提供六个 Terminal 来让使用者登入, 切换的方式为使用:[Ctrl] [Alt] [F1]~[F6]的组合按钮。 那这六个终端接口如何命名呢,系统会将[F1] ~ [F6]命名为 tty1…