def read_data(self): r""" Read DOS, as calculated and written by VASP Returns ------- E : numpy.ndarray energy points (in eV) DOS : numpy.ndarray DOS points (in 1/eV) """ # read first line line = self.readline() # NIONS, NIONS, JOBPAR_, WDES%INCDIJ line = self.readline() # AOMEGA, LATT_CUR%ANORM(1:3) *1e-10, POTIM * 1e-15 line = self.readline() # TEMP line = self.readline() # ' CAR ' line = self.readline() # name line = self.readline().split() Emax = float(line[0]) Emin = float(line[1]) NE = int(line[2]) Ef = float(line[3]) E = np.empty([NE], np.float32) # Determine output line = arrayf(self.readline().split()) ns = (len(line) - 1) // 2 DOS = np.empty([ns, NE], np.float32) E[0] = line[0] DOS[:, 0] = line[1:ns+1] for ie in range(1, NE): line = arrayf(self.readline().split()) E[ie] = line[0] DOS[:, ie] = line[1:ns+1] return E - Ef, DOS
def _voronoi_hirshfeld_charges(): """ Read output from Voronoi/Hirshfeld charges """ nonlocal pd # Expecting something like this: # Voronoi Atomic Populations: # Atom # dQatom Atom pop S Sx Sy Sz Species # 1 -0.02936 4.02936 0.00000 -0.00000 0.00000 0.00000 C # Define the function that parses the charges def _parse_charge(line): atom_idx, *vals, symbol = line.split() # assert that this is a proper line # this should catch cases where the following line of charge output # is still parseable atom_idx = int(atom_idx) return list(map(float, vals)) # first line is the header header = ( self.readline().replace("dQatom", "dq") # dQatom in master .replace(" Qatom", " dq") # Qatom in 4.1 .replace("Atom pop", "e") # not found in 4.1 .split())[2:-1] # We have found the header, prepare a list to read the charges atom_charges = [] line = ' ' while line != "": try: line = self.readline() charge_vals = _parse_charge(line) atom_charges.append(charge_vals) except: # We already have the charge values and we reached a line that can't be parsed, # this means we have reached the end. break if pd is None: # not as_dataframe return _a.arrayf(atom_charges) # determine how many columns we have # this will remove atom indices and species, so only inside ncols = len(atom_charges[0]) assert ncols == len(header) # the precision is limited, so no need for double precision return pd.DataFrame(atom_charges, columns=header, dtype=np.float32, index=pd.RangeIndex(stop=len(atom_charges), name="atom"))
def _empty_charge(): # return for single value with nan values return _a.arrayf([[None]])