@@ -43,18 +43,16 @@ class NebTaskDoc(BaseModel, extra="allow"):
43
43
None ,
44
44
description = "The initial and final configurations (reactants and products) of the barrier." ,
45
45
)
46
- endpoint_energies : Optional [Sequence [float ]] = Field (
47
- None ,
48
- description = "Energies of the endpoint structures."
46
+ endpoint_energies : Optional [Sequence [float ]] = Field (
47
+ None , description = "Energies of the endpoint structures."
49
48
)
50
- endpoint_calculations : Optional [list [Calculation ]] = Field (
51
- None ,
52
- description = "Calculation information for the endpoint structures"
49
+ endpoint_calculations : Optional [list [Calculation ]] = Field (
50
+ None , description = "Calculation information for the endpoint structures"
53
51
)
54
- endpoint_objects : Optional [list [dict ]] = Field (
52
+ endpoint_objects : Optional [list [dict ]] = Field (
55
53
None , description = "VASP objects for each endpoint calculation."
56
54
)
57
- endpoint_directories : Optional [list [str ]] = Field (
55
+ endpoint_directories : Optional [list [str ]] = Field (
58
56
None , description = "List of the directories for the endpoint calculations."
59
57
)
60
58
@@ -140,25 +138,33 @@ def set_barriers(self) -> Self:
140
138
def num_images (self ) -> int :
141
139
"""Return the number of VASP calculations / number of images performed."""
142
140
return len (self .image_directories )
143
-
141
+
144
142
@property
145
143
def energies (self ) -> list [float ]:
146
144
"""Return the endpoint (optional) and image energies."""
147
145
if self .endpoint_energies is not None :
148
- return [self .endpoint_energies [0 ], * self .image_energies , self .endpoint_energies [1 ]]
146
+ return [
147
+ self .endpoint_energies [0 ],
148
+ * self .image_energies ,
149
+ self .endpoint_energies [1 ],
150
+ ]
149
151
return self .image_energies
150
152
151
153
@property
152
154
def structures (self ) -> list [Structure ]:
153
155
"""Return the endpoint and image structures."""
154
- return [self .endpoint_structures [0 ], * self .image_structures , self .endpoint_structures [1 ]]
155
-
156
+ return [
157
+ self .endpoint_structures [0 ],
158
+ * self .image_structures ,
159
+ self .endpoint_structures [1 ],
160
+ ]
161
+
156
162
@classmethod
157
163
def from_directory (
158
164
cls ,
159
165
dir_name : Union [Path , str ],
160
166
volumetric_files : Tuple [str , ...] = _VOLUMETRIC_FILES ,
161
- store_calculations : bool = True ,
167
+ store_calculations : bool = True ,
162
168
** neb_task_doc_kwargs ,
163
169
) -> Self :
164
170
"""
@@ -172,7 +178,7 @@ def from_directory(
172
178
173
179
neb_directories = sorted (dir_name .glob ("[0-9][0-9]" ))
174
180
175
- if (ep_calcs := neb_task_doc_kwargs .pop ("endpoint_calculations" , None ) ) is None :
181
+ if (ep_calcs := neb_task_doc_kwargs .pop ("endpoint_calculations" , None )) is None :
176
182
endpoint_directories = [neb_directories [0 ], neb_directories [- 1 ]]
177
183
endpoint_structures = [
178
184
Structure .from_file (zpath (f"{ endpoint_dir } /POSCAR" ))
@@ -181,12 +187,8 @@ def from_directory(
181
187
endpoint_energies = None
182
188
else :
183
189
endpoint_directories = neb_task_doc_kwargs .pop ("endpoint_directories" )
184
- endpoint_structures = [
185
- ep_calc .output .structure for ep_calc in ep_calcs
186
- ]
187
- endpoint_energies = [
188
- ep_calc .output .energy for ep_calc in ep_calcs
189
- ]
190
+ endpoint_structures = [ep_calc .output .structure for ep_calc in ep_calcs ]
191
+ endpoint_energies = [ep_calc .output .energy for ep_calc in ep_calcs ]
190
192
191
193
image_directories = neb_directories [1 :- 1 ]
192
194
@@ -216,8 +218,7 @@ def from_directory(
216
218
task_state = (
217
219
TaskState .SUCCESS
218
220
if all (
219
- calc .has_vasp_completed == TaskState .SUCCESS
220
- for calc in calcs_to_check
221
+ calc .has_vasp_completed == TaskState .SUCCESS for calc in calcs_to_check
221
222
)
222
223
else TaskState .FAILED
223
224
)
@@ -247,11 +248,11 @@ def from_directory(
247
248
248
249
return cls (
249
250
endpoint_structures = endpoint_structures ,
250
- endpoint_energies = endpoint_energies ,
251
- endpoint_directories = [str (ep_dir ) for ep_dir in endpoint_directories ],
252
- endpoint_calculations = ep_calcs if store_calculations else None ,
251
+ endpoint_energies = endpoint_energies ,
252
+ endpoint_directories = [str (ep_dir ) for ep_dir in endpoint_directories ],
253
+ endpoint_calculations = ep_calcs if store_calculations else None ,
253
254
image_calculations = image_calculations if store_calculations else None ,
254
- image_structures = image_structures ,
255
+ image_structures = image_structures ,
255
256
dir_name = str (dir_name ),
256
257
image_directories = [str (img_dir ) for img_dir in image_directories ],
257
258
orig_inputs = inputs ["orig_inputs" ],
@@ -271,7 +272,7 @@ def from_directories(
271
272
endpoint_directories : list [str | Path ],
272
273
neb_directory : str | Path ,
273
274
volumetric_files : Tuple [str , ...] = _VOLUMETRIC_FILES ,
274
- ** neb_task_doc_kwargs
275
+ ** neb_task_doc_kwargs ,
275
276
) -> Self :
276
277
"""
277
278
Return an NebTaskDoc from endpoint and NEB calculation directories.
@@ -282,12 +283,26 @@ def from_directories(
282
283
endpoint_calculations = [None for _ in range (2 )]
283
284
endpoint_objects = [None for _ in range (2 )]
284
285
for idx , endpoint_dir in enumerate (endpoint_directories ):
285
- vasp_files = _find_vasp_files (endpoint_dir , volumetric_files = volumetric_files )
286
- ep_key = "standard" if vasp_files .get ("standard" ) else "relax" + str (max (
287
- int (k .split ("relax" )[- 1 ]) for k in vasp_files if k .startswith ("relax" )
288
- ))
286
+ vasp_files = _find_vasp_files (
287
+ endpoint_dir , volumetric_files = volumetric_files
288
+ )
289
+ ep_key = (
290
+ "standard"
291
+ if vasp_files .get ("standard" )
292
+ else "relax"
293
+ + str (
294
+ max (
295
+ int (k .split ("relax" )[- 1 ])
296
+ for k in vasp_files
297
+ if k .startswith ("relax" )
298
+ )
299
+ )
300
+ )
289
301
290
- endpoint_calculations [idx ], endpoint_objects [idx ] = Calculation .from_vasp_files (
302
+ (
303
+ endpoint_calculations [idx ],
304
+ endpoint_objects [idx ],
305
+ ) = Calculation .from_vasp_files (
291
306
dir_name = endpoint_dir ,
292
307
task_name = f"NEB endpoint { idx + 1 } " ,
293
308
vasprun_file = vasp_files [ep_key ]["vasprun_file" ],
@@ -299,16 +314,17 @@ def from_directories(
299
314
"parse_potcar_file" : False ,
300
315
},
301
316
)
302
-
317
+
303
318
return cls .from_directory (
304
319
neb_directory ,
305
320
volumetric_files = volumetric_files ,
306
- endpoint_calculations = endpoint_calculations ,
307
- endpoint_objects = endpoint_objects ,
308
- endpoint_directories = endpoint_directories ,
309
- ** neb_task_doc_kwargs
321
+ endpoint_calculations = endpoint_calculations ,
322
+ endpoint_objects = endpoint_objects ,
323
+ endpoint_directories = endpoint_directories ,
324
+ ** neb_task_doc_kwargs ,
310
325
)
311
-
326
+
327
+
312
328
def neb_barrier_spline_fit (
313
329
energies : Sequence [float ],
314
330
spline_kwargs : dict | None = None ,
0 commit comments