Learn VASP The Hard Way (Ex30):进阶前的准备(三)

2017-08-02


Ex30 进阶前的准备(三)

自动生成POTCAR的脚本

 

前面我们介绍了KPOINTS的小脚本的写法,本节我们主要讲解一下生成POTCAR的脚本。学习完本节,脚本的神秘色彩基本烟消云散,大家都可以尝试写自己的脚本了。提前说明三点:

1)Windows用户不要用记事本写脚本;

2)Windows用户写完脚本后,在服务器上先运行: dos2unix XXX  (XXX 是你的脚本名)

3)Windows用户,如果计算出错,第一个要排除的是自己提交任务前有没有运行:dos2unix.

 



手动示例:

 

比如我们POSCAR中包含有Cu C H O 四种种元素,那么我们就需要按照顺序生成一个对应的POTCAR。首先回顾一下前面介绍的POTCAR的制备方法:

1.1)获取这四个元素各自的POTCAR:并命名成POTCAR_Cu,POTCAR_C,POTCAR_H,POTCAR_O

1.2)使用cat 命令将这四个POTCAR合并在一起:

cat POTCAR_Cu  POTCAR_C POTCAR_H POTCAR_O > POTCAR

 

前面我们学过了 > 的使用。分步练习:

第一步将这些元素的POTCAR全部打印出来:

cat  POTCAR_Cu  POTCAR_C POTCAR_H POTCAR_O 

第二步:将打印出来的内容通过 >  保存到最终的POTCAR里面。

 



我们写脚本的目的: 自动从赝势库中提取所需元素的POTCAR并将它们合并在一起。

 


图中我们赝势库的目录为:

/home/oldhome/nlopez/PPS/pot_for_vasp5.4/PBE/potpaw_PBE

 

查看一下我们所感兴趣的这几个元素的目录:

 


从图中可以看出来,在Cu,C,H,O四个目录下均有一个对应的POTCAR

 

所以我们可以使用命令:(不将这几个POTCAR先保存到当前目录下,直接调用赝势库中的POTCAR)

 

cat  /home/oldhome/nlopez/PPS/pot_for_vasp5.4/PBE/potpaw_PBE/Cu/POTCAR

/home/oldhome/nlopez/PPS/pot_for_vasp5.4/PBE/potpaw_PBE/C/POTCAR

/home/oldhome/nlopez/PPS/pot_for_vasp5.4/PBE/potpaw_PBE/H/POTCAR

/home/oldhome/nlopez/PPS/pot_for_vasp5.4/PBE/potpaw_PBE/O/POTCAR

> POTCAR

 

注意:不同的课题组,这四个目录下的文件格式可能会不同:

格式1:如图中的例子,这里直接是POTCAR,

格式2:有些是POTCAR.gz 格式的,此时我们有两个选择:

1)先通过该命令解压缩:gunzip  POTCAR.gz  ,获得对应的POTCAR

2)不解压缩,只提取POTCAR.gz里面的内容,命令为: gunzip  –c  POTCAR.gz

格式3:有些是POTCAR.Z 格式的

1)先解压缩命令:gunzip  POTCAR.z 获得对应的POTCAR

2)不解压缩,只提取POTCAR.z的内容,命令: zcat POTCAR.z 

3)不解压缩,还可以使用前面的命令: gunzip –c POTCAR. z

 

前面的zcat 和 gunzip –c 命令和 cat 是等效的。(记住这一点,后面用得着)

建议大家:要么全部都采用压缩的格式,要么都统一用POTCAR,不要两者混着。统一起来是为了方便处理。此外,前面命令中的路径重复了好多次,又长又麻烦,我们需要简化一下。

 



脚本预览:

 

首先看下自动生成POTCAR的脚本,大家尽量先不看下面的解释,自己理解一下脚本的整个框架和运行的流程;

 

#!/usr/bin/env bash

# Create a GGA_PAW POTCAR file byconcatenation of POTCAR files

# BigBro 2017-07-31 TGN

# To Use it: potcar.sh Cu C H O

 

# Define local potpaw_GGA pseudopotentialrepository:

repo="/home/oldhome/nlopez/PPS/pot_for_vasp5.4/PBE/potpaw_PBE"

 

# Check if older version of POTCAR ispresent

if [ -f POTCAR ] ; then

 mv -f POTCAR old-POTCAR

 echo " ** Warning: old POTCAR file found and renamed to 'old-POTCAR'."

fi

 

# Main loop - concatenate the appropriatePOTCARs (or archives)

for i in $*

do

 if test -f $repo/$i/POTCAR ; then

  cat $repo/$i/POTCAR>> POTCAR

 elif test -f $repo/$i/POTCAR.Z ; then

 zcat $repo/$i/POTCAR.Z >> POTCAR

 elif test -f $repo/$i/POTCAR.gz ; then

 gunzip -c $repo/$i/POTCAR.gz >> POTCAR

 else

 echo " ** Warning: No suitable POTCAR for element '$i' found!! Skipped thiselement."

 fi

done

 



讲解,这个脚本里面:

1)首先我们先设定赝势库的目录;

repo="/home/oldhome/nlopez/PPS/pot_for_vasp5.4/PBE/potpaw_PBE"

等号前后不能有空格!!!

 

2)然后我们检查一下当前目录下是否存在POTCAR,如果存在的话,将其重命名为:

POTCAR-old, 并输出警告信息。




这里我们学到的是 if 句型:if [ ] ; then; fi

[] 中间是if判断的条件,如果成立,则继续执行then后面的动作。

if [ -f POTCAR ]; then  意思是如果存在POTCAR这个文件,那么…

注意:

a)[ ] 和里面的内容 –f POTCAR 要通过空格分开。所以:

if [-f POTCAR ] ([ 和-f之间没有空格)

if [ -f POTCAR] ( POTCAR 和] 之间没有空格)

if [-f POTCAR] (-f,POTCAR和 [] 之间都没有空格)

这三种写法都是错误的;if [  -f POTCAR  ] 是正确的

b)then 后面如果另起一行的话,分号 () 可加可不加;

c) then 后面的内容如果和then 在同一行,必须加上分号() ,前后有无空格均可,建议加上,这样语言会很清晰;

c)  then 后面的命令执行完毕后,要加上 fi 结束。同理,如果fi 另起一行,则前面可以不加;如果fi 和 then 后面执行的命令在一行,前面需要加上分号()。

 



3)生成新的POTCAR文件;



这里我们用到的是一个for循环:

a)  for i in $*

这一行的意思是,对于命令后面的所有参数(arguments),前面一节我们已经学过了$1 $2 ... 的含义,这里用的$* 可以让我们在命令后面加任意数目的参数;

因为另起了一行,后面加不加分号(;)不重要。

b) do  执行的意思,

c)do后面有个if 语句,如果目录下面是POTCAR的话,那么使用cat 命令将所有$*对应的POTCAR输出到最新的POTCAR中,注意,这里我们用到的是>>; 因为for循环是对于后面的参数挨个执行的。

d) 有两个elif,判断目录下的另外两个POTCAR文件的格式,如果是POTCAR.Z 文件的话,则使用zcat 将其输出到最新的POTCAR;如果是POTCAR.gz 文件的话,则使用gunzip –c 命令。

e)else 指的是除了前面三种以外的情况,如果POTCAR,POTCAR.Z或者POTCAR.gz都不存在,那么使用echo命令,输出警告,提醒用户检查。

f)使用fi 结束if 语句,

g)使用 done 结束 for 循环。

  



运行脚本:


3.1)赋予脚本可执行权限,然后将其转移到主目录下的bin文件夹中。

chmod u+x potcar.sh

mv potcar.sh ~/bin



3.2)图中1 指的是生成对应的Cu C H O 的POTCAR文件

3.3)图中2 指的是如果当前目录下存在POTCAR,脚本会给出警告,将其重命名为old-POTCAR,然后生成新的POTCAR文件;

3.4)图中3 指的是如果我们元素不存在或者输入的时候出错,给出警告。

 



脚本分析:

 

4.1)生成一些特殊的POTCAR文件:


我们知道,每一个元素存在好几个不同的POTCAR,如图:



当我们需要使用 Cu_pv, C_s 和H1.5对应的POTCAR时,我们需要这样执行命令:



4.2) 因此,如果我们使用脚本的时候直接输入元素符号,读取的是与该元素符号相对应文件下的POTCAR。

 



读取POSCAR,自动生成POTCAR 防止出错的一个秘诀

 

在我们的计算中,可以通过读取POSCAR中的元素信息,生成对应的POTCAR文件,这样可以避免POSCAR中元素和POTCAR中不一致的情况。那么我们需要怎么做呢?

 

5.1 首先我们要获取POSCAR中的元素信息: 查看一下POSCAR文件:



我们发现元素信息在第6行,因此可以这样提取:



5.2 使用我们刚刚写出来的脚本,通过使用$()调用前面命令的结果: (将获取的元素信息作为脚本命令的参数)



大功告成!!!!

 



5.3 不想每次输入这么长的命令:可以将其写进 ~/.bashrc文件中:

 

alias pos2pot="potcar.sh  $(head -n 6 POSCAR  | tail -n 1)"



5.4 看完上面的部分,相信大家已经可以掌握很多内容了,额外福利,大师兄本人并没有使用head -n 6 POSCAR  | tail -n 1 来获取POSCAR中的元素信息。而是使用的sed命令:





扩展练习:

 

6.1)手动将这个脚本打一遍,理解里面的内容,如果出错了,对比我的脚本,进行改正,直至可以正确运行为止;

6.2)去官网查看POTCAR相关的内容,了解每一个元素不同的POTCAR之间的区别,例如:Cu 和 Cu_pv

6.3) 复习alias,学习本文第5节的方法,思考一下,如何通过操控脚本,避免计算中的一些失误,有了自己的想法后,通过脚本付诸实践。

 



总结:

 

写到这里,相信大家对于Linux系统下的一些基本操作已经熟练掌握了,脚本的怎么写,怎么去运行,心里也有了一个大致的了解,至少不会感觉写脚本是多么牛逼的工作了。这些内容都是我们保证计算准确,高效的很重要的一个因素。希望大家可以熟练掌握,最关键的是,要硬着头皮去练习,脚本看起来简单,等你写的时候就会出现各种各样的错误,只有不断练习,才能写出漂亮的脚本,提高自己的工作效率。

 

脚本已经上传至QQ群文件,也可百度网盘下载:链接:http://pan.baidu.com/s/1geC0IsF  密码:r4om

本网站由阿里云提供云计算及安全服务