@@ -1895,6 +1895,50 @@ def get_fc_from_self_consistency(self, subtract_sscha = False, return_error = Fa
18951895
18961896 return new_phi
18971897
1898+ def get_preconditioned_gradient_parallel (self , * args , ** kwargs ):
1899+ """
1900+ Compute the gradient using multiprocessing.
1901+ For documentation, see get_preconditioned_gradient
1902+ """
1903+
1904+ print ("force length:" , len (self .force_computed ))
1905+
1906+ def work_function (argument ):
1907+ print ("force length [inside]:" , len (self .force_computed ))
1908+ ensemble_start_config , ensemble_end_config = argument
1909+ mask = np .zeros (self .N , dtype = bool )
1910+ mask [ensemble_start_config : ensemble_end_config ] = True
1911+ print ("mask length:" , np .sum (mask .astype (int ))," total N:" , len (mask ))
1912+ new_ensemble = self .split (mask )
1913+
1914+ gradient , _ = new_ensemble .get_preconditioned_gradient (* args , ** kwargs )
1915+
1916+ av_ensemble = np .sum (new_ensemble .rho )
1917+
1918+ return gradient * av_ensemble
1919+
1920+ nproc = CC .Settings .GetNProc ()
1921+ list_of_inputs = []
1922+ index = 0
1923+ for i in range (nproc ):
1924+ start_config = index
1925+ index += self .N // nproc
1926+ if i < self .N % nproc :
1927+ index += 1
1928+ end_config = index
1929+
1930+ list_of_inputs .append ( (start_config , end_config ) )
1931+
1932+ gradient = CC .Settings .GoParallel (work_function , list_of_inputs , "+" )
1933+ gradient /= np .sum (self .rho )
1934+
1935+ return gradient , np .zeros_like (gradient ) + 1
1936+
1937+
1938+
1939+
1940+
1941+
18981942 def get_preconditioned_gradient (self , subtract_sscha = True , return_error = False ,
18991943 use_ups_supercell = True , preconditioned = 1 ,
19001944 fast_grad = False , verbose = True , timer = None ):
@@ -1910,7 +1954,7 @@ def get_preconditioned_gradient(self, subtract_sscha = True, return_error = Fals
19101954
19111955 .. math::
19121956
1913- \\ Phi_{ab} = \\ sum_c \\ upsilon_ {ac} \\ left< u_c f_a\\ right>_{\\ Phi}
1957+ \\ Phi_{ab} = \\ sum_c \\ Upsilon_ {ac} \\ left< u_c f_a\\ right>_{\\ Phi}
19141958
19151959 The previous equation is true only if the :math:`\\ Phi` matrix is the solution
19161960 of the SCHA theory. Here :math:`\\ vec u` are the displacements of the configurations
@@ -3109,9 +3153,12 @@ def compute_ensemble(self, calculator, compute_stress = True, stress_numerical =
31093153 else :
31103154 computing_ensemble .get_energy_forces (calculator , compute_stress , stress_numerical , verbose = verbose )
31113155
3156+ print ("CE BEFORE MERGE:" , len (self .force_computed ))
3157+
31123158 if should_i_merge :
31133159 # Remove the noncomputed ensemble from here, and merge
31143160 self .merge (computing_ensemble )
3161+ print ("CE AFTER MERGE:" , len (self .force_computed ))
31153162
31163163 print ('ENSEMBLE ALL PROPERTIES:' , self .all_properties )
31173164
@@ -3177,6 +3224,11 @@ def split(self, split_mask):
31773224 N = np .sum (split_mask .astype (int ))
31783225 ens = Ensemble (self .dyn_0 , self .T0 , self .dyn_0 .GetSupercell ())
31793226 ens .init_from_structures (structs )
3227+ print ("Split length:" , len (split_mask ))
3228+ print ("original force legnth:" , len (self .force_computed ))
3229+ print ("Expected length:" , len (ens .force_computed ))
3230+ print ("Splitting force length:" , len (self .force_computed [split_mask ]))
3231+
31803232 ens .force_computed [:] = self .force_computed [split_mask ]
31813233 ens .stress_computed [:] = self .stress_computed [split_mask ]
31823234 ens .energies [:] = self .energies [split_mask ]
@@ -3199,7 +3251,7 @@ def remove_noncomputed(self):
31993251 It may be used to run a minimization even if the ensemble was not completely calculated.
32003252 """
32013253
3202- good_mask = self .force_computed
3254+ good_mask = np . copy ( self .force_computed )
32033255 if self .has_stress :
32043256 good_mask = good_mask & self .stress_computed
32053257
@@ -3211,6 +3263,8 @@ def remove_noncomputed(self):
32113263 self .sscha_energies = self .sscha_energies [good_mask ]
32123264 self .xats = self .xats [good_mask , :, :]
32133265 self .u_disps = self .u_disps [good_mask , :]
3266+ self .force_computed = self .force_computed [good_mask ]
3267+ self .stress_computed = self .stress_computed [good_mask ]
32143268
32153269 self .structures = [self .structures [x ] for x in np .arange (len (good_mask ))[good_mask ]]
32163270 self .all_properties = [self .all_properties [x ] for x in np .arange (len (good_mask ))[good_mask ]]
@@ -3263,6 +3317,7 @@ def get_energy_forces(self, ase_calculator, compute_stress = True, stress_numeri
32633317
32643318 # Setup the calculator for each structure
32653319 parallel = False
3320+ print ("Force computed shape:" , len (self .force_computed ))
32663321 if __MPI__ :
32673322 comm = MPI .COMM_WORLD
32683323 size = comm .Get_size ()
@@ -3419,6 +3474,7 @@ def get_energy_forces(self, ase_calculator, compute_stress = True, stress_numeri
34193474 # Reshape the arrays
34203475 self .forces [:, :, :] = np .reshape (total_forces , (N_rand , self .current_dyn .structure .N_atoms * np .prod (self .supercell ), 3 ), order = "C" )
34213476 self .force_computed [:] = True
3477+ print ("Force computed shape:" , len (self .force_computed ))
34223478
34233479 if compute_stress :
34243480 self .stresses [:,:,:] = np .reshape (total_stress , (N_rand , 3 , 3 ), order = "C" )
0 commit comments