-
Notifications
You must be signed in to change notification settings - Fork 4
/
cube_operations.py
125 lines (98 loc) · 3.07 KB
/
cube_operations.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
#!/usr/bin/env python
import os
import numpy as np
import time
import copy
import sys
import argparse
ang_2_bohr = 1.0/0.52917721067
hart_2_ev = 27.21138602
from cp2k_spm_tools import common, cube, cube_utils
parser = argparse.ArgumentParser(
description='Operations on gaussian cube files.')
parser.add_argument(
'cubes',
metavar='FILENAME',
nargs='+',
help='Gaussian cube files.')
parser.add_argument(
'operations',
metavar='OP',
type=str,
help='Operations to apply to each cube. Enclose in quotation marks.')
parser.add_argument(
'--proj_1d',
metavar='IDs',
type=str,
default='no',
help=("Projects to 'x', 'y' or 'z' dim, possibly averaging (e.g. 'z avg').")
)
parser.add_argument(
'--skip_result_cube',
action='store_true',
help=("Don't write the result cube.")
)
parser.add_argument(
'--add_artif_core',
action='store_true',
help=("Adds artifical core charge to result cube (mainly for Bader analysis).")
)
time0 = time.time()
args = parser.parse_args()
result = None
operations = args.operations.split()
if len(operations) != len(args.cubes):
print("Error: didn't find match between cubes and operations.")
print("Did you forget to enclose operations in quotation marks?")
exit(1)
for i_c, cube_file in enumerate(args.cubes):
time1 = time.time()
c = cube.Cube()
print("Reading %s..." % cube_file)
c.read_cube_file(cube_file)
if result is None:
result = copy.deepcopy(c)
result.data.fill(0)
if np.any(np.abs(c.cell - result.cell) > 1e-4):
print("Error: cube cell doesn't match: ", cube_file)
exit(1)
if np.any(c.data.shape != result.data.shape):
print("Error: cube shape doesn't match: ", cube_file)
exit(1)
op = operations[i_c]
if op == "+":
result.data += c.data
elif op == "-":
result.data -= c.data
elif op == "*":
result.data *= c.data
elif op == "/":
result.data /= c.data
print("%s done, time: %.2fs"%(cube_file, (time.time() - time1)))
if args.add_artif_core:
cube_utils.add_artif_core_charge(result)
if not args.skip_result_cube:
print("Writing result...")
result.write_cube_file("./result.cube")
proj_1d_ids = args.proj_1d.split()
if not "no" in proj_1d_ids:
avg = 'avg' in proj_1d_ids
proj_dims = []
if 'x' in proj_1d_ids:
proj_dims.append(0)
if 'y' in proj_1d_ids:
proj_dims.append(1)
if 'z' in proj_1d_ids:
proj_dims.append(2)
for pd in proj_dims:
if avg:
data_1d = np.mean(result.data, axis=tuple({0, 1, 2} - {pd}))
else:
data_1d = np.sum(result.data, axis=tuple({0, 1, 2} - {pd}))
x_arr = result.origin[pd] + np.linspace(0.0, result.cell[pd, pd], result.data.shape[pd])
x_arr /= ang_2_bohr
save_arr = np.column_stack((x_arr, data_1d))
avg_str = "_avg" if avg else ""
fname = "./proj_1d_%d" % pd + avg_str + ".txt"
np.savetxt(fname, save_arr)
print("Finished, total time: %.2fs"%(time.time() - time0))