从Gaussian 09的Hartree-Fock计算的fchk文件转换到Columbus的mocoef文件的脚本

来源:互联网 发布:mac git冲突解决 编辑:程序博客网 时间:2024/05/16 07:22

这个脚本用于将Gaussian 09的Hartree-Fock计算的.fchk文件转换到Columbus软件使用的mocoef文件。

需要说明的是,测试工作还不完善,不保证此脚本的正确性。

注意:两个软件所使用的基组以及对称性等等必须完全一致!

#! /usr/bin/perl# code by luozhen# ATTENTION: MAKE SURE that the SAME BASIS SET has been used in the two softwares.# results saved in the file "mocoef"# you MUST have the access to write in the work directory.open (Columbus, ">mocoef") or die "Can not create file \"mocoef\"!";# read input data# use command as "./hfg09tocol.pl inputfile" in bash shell.while (<>) {push @lines, $_;}# check necessary infowhile ($id < @lines) {        if ($lines[$id] =~ m/Number of electrons.*([0-9][0-9]+)/) {                $count_electrons = $1;        } elsif ($lines[$id] =~ m/basis functions.*([0-9][0-9]+)/) {$count_basis_func = $1;} elsif ($lines[$id] =~ m/independent functions.*([0-9][0-9]+)/) {$count_indp_func = $1;} elsif ($lines[$id] =~ m/Alpha Orbital Energies/) {$id_start_energy = $id + 1;} elsif ($lines[$id] =~ m/Alpha MO coefficients/) {$id_start_mocoef = $id + 1;$id_end_energy = $id - 1;} elsif ($lines[$id] =~ m/Total SCF Density/) {$id_end_mocoef = $id - 1;}$id++;}# read orbital energies$lines_count_orbeng = $id_end_energy - $id_start_energy + 1;@data_orbeng = splice @lines, $id_start_energy, $lines_count_orbeng;# read MO coefficients$lines_count_mocoef = $id_end_mocoef - $id_start_mocoef + 1;$id_start_mocoef -= $lines_count_orbeng;@data_mocoef = splice @lines, $id_start_mocoef, $lines_count_mocoef;# necessary lines in the file "mocoef"print Columbus " 2mocoef\nheader\n" . "\t" x 5 . " 2\nHermit Integral Program : Gaussian 09 \nmo coefficients generated by Gaussian 09\n" . "\t" x 5 . " 1\n" . "\t" x 5 . "$count_basis_func" . "\t" x 5 . "$count_indp_func\n A\n";# MO coefficients, printprint Columbus "mocoef\n(1p4e16.8)\n";{        my @numbers;        foreach (@data_mocoef) {                my @temp = split;                push @numbers, @temp;        }        my $count = 0;        my $counts = @numbers;        while ($count < $counts) {                printf Columbus "%16s", $numbers[$count];                if (($count + 1) % 4 == 0) {# 4 numbers per line                        print Columbus "\n";                        $count ++;                } elsif (($count + 1) % $count_basis_func == 0) {                        print Columbus "\n";                        splice @numbers, 0, $count_basis_func;                        $counts = @numbers;                        $count = 0;                } else {                        $count ++;                }        }}# orbocc, calculate and print# there's no data about orbitals occupation in Gaussian's *.fchk file.# so I have to do some calculations myself,# and I can not ensure that the result of the following block is perfectly correct.print Columbus "orbocc\n(1p4e16.8)\n";{        my $count = 0;        my @numbers;        my $count_double_occ = $count_electrons / 2;        if ($count_electrons % 2 == 0) {                while ($count < $count_basis_func) {                        if ($count < $count_double_occ) {                                push @numbers, "2.00000000E+00";                        } else {                                push @numbers, "0.00000000E+00";                        }                        $count ++;                }        } else {                while ($count < $count_basis_func) {                        if ($count < $count_double_occ) {                                push @numbers, "2.00000000E+00";                        } elsif ($count < $count_double_occ) {                                push @numbers, "1.00000000E+00";                        } else {                                push @numbers, "0.00000000E+00";                        }                        $count ++;                }        }        my $count = 0;        my $counts = @numbers;        while ($count < $counts) {                printf Columbus "%16s", $numbers[$count];                if (($count + 1) % 4 == 0) {# 4 numbers per line                        print Columbus "\n";                }                $count ++;        }        print Columbus "\n";}                # energy, printprint Columbus "energy\n(1p4e16.8)\n";{        my @numbers;        foreach (@data_orbeng) {                my @temp = split;                push @numbers, @temp;        }        my $count = 0;        my $counts = @numbers;        while ($count < $counts) {                printf Columbus "%16s", $numbers[$count];                if (($count + 1) % 4 == 0) {# 4 numbers per line                        print Columbus "\n";                }                $count ++;        }        print Columbus "\n";}


0 0
原创粉丝点击