diff --git a/doc/source/conf.py b/doc/source/conf.py index f7b1c77..fdfbf5b 100644 --- a/doc/source/conf.py +++ b/doc/source/conf.py @@ -221,7 +221,13 @@ # (source start file, target name, title, # author, documentclass [howto, manual, or own class]). latex_documents = [ - ("index", "diffpy.structure.tex", "diffpy.structure Documentation", ab_authors, "manual"), + ( + "index", + "diffpy.structure.tex", + "diffpy.structure Documentation", + ab_authors, + "manual", + ), ] # The name of an image file (relative to this directory) to place at the top of @@ -249,7 +255,15 @@ # One entry per manual page. List of tuples # (source start file, name, description, authors, manual section). -man_pages = [("index", "diffpy.structure", "diffpy.structure Documentation", ab_authors, 1)] +man_pages = [ + ( + "index", + "diffpy.structure", + "diffpy.structure Documentation", + ab_authors, + 1, + ) +] # If true, show URL addresses after external links. # man_show_urls = False diff --git a/pyproject.toml b/pyproject.toml index dd1150c..d977015 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -55,7 +55,7 @@ namespaces = false # to disable scanning PEP 420 namespaces (true by default) dependencies = {file = ["requirements/pip.txt"]} [tool.black] -line-length = 115 +line-length = 79 include = '\.pyi?$' exclude = ''' /( diff --git a/src/diffpy/structure/_legacy_importer.py b/src/diffpy/structure/_legacy_importer.py index e37a907..66302c6 100644 --- a/src/diffpy/structure/_legacy_importer.py +++ b/src/diffpy/structure/_legacy_importer.py @@ -80,7 +80,11 @@ def exec_module(self, module): # ---------------------------------------------------------------------------- # show deprecation warning for diffpy.Structure -warn(WMSG.format("diffpy.Structure", "diffpy.structure"), DeprecationWarning, stacklevel=2) +warn( + WMSG.format("diffpy.Structure", "diffpy.structure"), + DeprecationWarning, + stacklevel=2, +) # install meta path finder for diffpy.Structure submodules sys.meta_path.append(FindRenamedStructureModule()) diff --git a/src/diffpy/structure/apps/__init__.py b/src/diffpy/structure/apps/__init__.py index 6f0249a..15ad470 100644 --- a/src/diffpy/structure/apps/__init__.py +++ b/src/diffpy/structure/apps/__init__.py @@ -13,5 +13,4 @@ # ############################################################################## -"""Script applications that use the `diffpy.structure` package. -""" +"""Script applications that use the `diffpy.structure` package.""" diff --git a/src/diffpy/structure/apps/anyeye.py b/src/diffpy/structure/apps/anyeye.py index b7904d8..f4bb5ce 100755 --- a/src/diffpy/structure/apps/anyeye.py +++ b/src/diffpy/structure/apps/anyeye.py @@ -71,7 +71,11 @@ def usage(style=None): myname = os.path.basename(sys.argv[0]) msg = __doc__.replace("anyeye", myname) if style == "brief": - msg = msg.split("\n")[1] + "\n" + "Try `%s --help' for more information." % myname + msg = ( + msg.split("\n")[1] + + "\n" + + "Try `%s --help' for more information." % myname + ) else: from diffpy.structure.parsers import inputFormats @@ -139,7 +143,10 @@ def convertStructureFile(pd): if pd["formula"]: formula = pd["formula"] if len(formula) != len(stru): - emsg = "Formula has %i atoms while structure %i" % (len(formula), len(stru)) + emsg = "Formula has %i atoms while structure %i" % ( + len(formula), + len(stru), + ) raise RuntimeError(emsg) for a, el in zip(stru, formula): a.element = el @@ -218,7 +225,9 @@ def main(): pd["watch"] = False try: opts, args = getopt.getopt( - sys.argv[1:], "f:whV", ["formula=", "watch", "viewer=", "formats=", "help", "version"] + sys.argv[1:], + "f:whV", + ["formula=", "watch", "viewer=", "formats=", "help", "version"], ) except getopt.GetoptError as errmsg: print(errmsg, file=sys.stderr) diff --git a/src/diffpy/structure/apps/transtru.py b/src/diffpy/structure/apps/transtru.py index 86c682d..6e4dbb0 100755 --- a/src/diffpy/structure/apps/transtru.py +++ b/src/diffpy/structure/apps/transtru.py @@ -50,7 +50,11 @@ def usage(style=None): myname = os.path.basename(sys.argv[0]) msg = __doc__.replace("transtru", myname) if style == "brief": - msg = msg.split("\n")[1] + "\n" + "Try `%s --help' for more information." % myname + msg = ( + msg.split("\n")[1] + + "\n" + + "Try `%s --help' for more information." % myname + ) else: from diffpy.structure.parsers import inputFormats, outputFormats @@ -99,7 +103,10 @@ def main(): print("'%s' is not valid output format" % outfmt, file=sys.stderr) sys.exit(2) except ValueError: - print("invalid format specification '%s' does not contain .." % args[0], file=sys.stderr) + print( + "invalid format specification '%s' does not contain .." % args[0], + file=sys.stderr, + ) sys.exit(2) # ready to do some real work try: diff --git a/src/diffpy/structure/atom.py b/src/diffpy/structure/atom.py index e531780..f964bb5 100644 --- a/src/diffpy/structure/atom.py +++ b/src/diffpy/structure/atom.py @@ -170,7 +170,9 @@ def msdLat(self, vl): lat = self.lattice or cartesian_lattice vln = numpy.array(vl, dtype=float) / lat.norm(vl) G = lat.metrics - rhs = numpy.array([G[0] * lat.ar, G[1] * lat.br, G[2] * lat.cr], dtype=float) + rhs = numpy.array( + [G[0] * lat.ar, G[1] * lat.br, G[2] * lat.cr], dtype=float + ) rhs = numpy.dot(rhs, vln) msd = numpy.dot(rhs, numpy.dot(self.U, rhs)) return msd @@ -202,7 +204,13 @@ def msdCart(self, vc): def __repr__(self): """String representation of this Atom.""" xyz = self.xyz - s = "%-4s %8.6f %8.6f %8.6f %6.4f" % (self.element, xyz[0], xyz[1], xyz[2], self.occupancy) + s = "%-4s %8.6f %8.6f %8.6f %6.4f" % ( + self.element, + xyz[0], + xyz[1], + xyz[2], + self.occupancy, + ) return s def __copy__(self, target=None): @@ -354,13 +362,19 @@ def _set_Uij(self, i, j, value): """ U11 = property( - lambda self: self._get_Uij(0, 0), lambda self, value: self._set_Uij(0, 0, value), doc=_doc_uii.format(0) + lambda self: self._get_Uij(0, 0), + lambda self, value: self._set_Uij(0, 0, value), + doc=_doc_uii.format(0), ) U22 = property( - lambda self: self._get_Uij(1, 1), lambda self, value: self._set_Uij(1, 1, value), doc=_doc_uii.format(1) + lambda self: self._get_Uij(1, 1), + lambda self, value: self._set_Uij(1, 1, value), + doc=_doc_uii.format(1), ) U33 = property( - lambda self: self._get_Uij(2, 2), lambda self, value: self._set_Uij(2, 2, value), doc=_doc_uii.format(2) + lambda self: self._get_Uij(2, 2), + lambda self, value: self._set_Uij(2, 2, value), + doc=_doc_uii.format(2), ) _doc_uij = """ @@ -371,13 +385,19 @@ def _set_Uij(self, i, j, value): """ U12 = property( - lambda self: self._get_Uij(0, 1), lambda self, value: self._set_Uij(0, 1, value), doc=_doc_uij.format(0, 1) + lambda self: self._get_Uij(0, 1), + lambda self, value: self._set_Uij(0, 1, value), + doc=_doc_uij.format(0, 1), ) U13 = property( - lambda self: self._get_Uij(0, 2), lambda self, value: self._set_Uij(0, 2, value), doc=_doc_uij.format(0, 2) + lambda self: self._get_Uij(0, 2), + lambda self, value: self._set_Uij(0, 2, value), + doc=_doc_uij.format(0, 2), ) U23 = property( - lambda self: self._get_Uij(1, 2), lambda self, value: self._set_Uij(1, 2, value), doc=_doc_uij.format(1, 2) + lambda self: self._get_Uij(1, 2), + lambda self, value: self._set_Uij(1, 2, value), + doc=_doc_uij.format(1, 2), ) # clean local variables diff --git a/src/diffpy/structure/expansion/supercell_mod.py b/src/diffpy/structure/expansion/supercell_mod.py index b5760a3..202232b 100644 --- a/src/diffpy/structure/expansion/supercell_mod.py +++ b/src/diffpy/structure/expansion/supercell_mod.py @@ -13,8 +13,7 @@ # ############################################################################## -"""This module contains functions for simple `Structure` manipulation. -""" +"""This module contains functions for simple `Structure` manipulation.""" import numpy @@ -69,7 +68,12 @@ def supercell(S, mno): return newS # back to business - ijklist = [(i, j, k) for i in range(mno[0]) for j in range(mno[1]) for k in range(mno[2])] + ijklist = [ + (i, j, k) + for i in range(mno[0]) + for j in range(mno[1]) + for k in range(mno[2]) + ] # numpy.floor returns float array mnofloats = numpy.array(mno, dtype=float) @@ -84,7 +88,9 @@ def supercell(S, mno): newS.__setitem__(slice(None), newAtoms, copy=False) # take care of lattice parameters - newS.lattice.setLatPar(a=mno[0] * S.lattice.a, b=mno[1] * S.lattice.b, c=mno[2] * S.lattice.c) + newS.lattice.setLatPar( + a=mno[0] * S.lattice.a, b=mno[1] * S.lattice.b, c=mno[2] * S.lattice.c + ) return newS diff --git a/src/diffpy/structure/lattice.py b/src/diffpy/structure/lattice.py index fb51de0..70c4dc7 100644 --- a/src/diffpy/structure/lattice.py +++ b/src/diffpy/structure/lattice.py @@ -32,7 +32,16 @@ # Helper Functions ----------------------------------------------------------- # exact values of cosd -_EXACT_COSD = {0.0: +1.0, 60.0: +0.5, 90.0: 0.0, 120.0: -0.5, 180.0: -1.0, 240.0: -0.5, 270.0: 0.0, 300.0: +0.5} +_EXACT_COSD = { + 0.0: +1.0, + 60.0: +0.5, + 90.0: 0.0, + 120.0: -0.5, + 180.0: -1.0, + 240.0: -0.5, + 270.0: 0.0, + 300.0: +0.5, +} def cosd(x): @@ -159,15 +168,21 @@ class Lattice(object): # properties ------------------------------------------------------------- a = property( - lambda self: self._a, lambda self, value: self.setLatPar(a=value), doc="The unit cell length *a*." + lambda self: self._a, + lambda self, value: self.setLatPar(a=value), + doc="The unit cell length *a*.", ) b = property( - lambda self: self._b, lambda self, value: self.setLatPar(b=value), doc="The unit cell length *b*." + lambda self: self._b, + lambda self, value: self.setLatPar(b=value), + doc="The unit cell length *b*.", ) c = property( - lambda self: self._c, lambda self, value: self.setLatPar(c=value), doc="The unit cell length *c*." + lambda self: self._c, + lambda self, value: self.setLatPar(c=value), + doc="The unit cell length *c*.", ) alpha = property( @@ -201,47 +216,105 @@ def unitvolume(self): rv = math.sqrt(1.0 + 2.0 * ca * cb * cg - ca * ca - cb * cb - cg * cg) return rv - volume = property(lambda self: self.a * self.b * self.c * self.unitvolume, doc="The unit cell volume.") + volume = property( + lambda self: self.a * self.b * self.c * self.unitvolume, + doc="The unit cell volume.", + ) - ar = property(lambda self: self._ar, doc="The cell length *a* of the reciprocal lattice.") + ar = property( + lambda self: self._ar, + doc="The cell length *a* of the reciprocal lattice.", + ) - br = property(lambda self: self._br, doc="The cell length *b* of the reciprocal lattice.") + br = property( + lambda self: self._br, + doc="The cell length *b* of the reciprocal lattice.", + ) - cr = property(lambda self: self._cr, doc="The cell length *c* of the reciprocal lattice.") + cr = property( + lambda self: self._cr, + doc="The cell length *c* of the reciprocal lattice.", + ) - alphar = property(lambda self: self._alphar, doc="The reciprocal cell angle *alpha* in degrees.") + alphar = property( + lambda self: self._alphar, + doc="The reciprocal cell angle *alpha* in degrees.", + ) - betar = property(lambda self: self._betar, doc="The reciprocal cell angle *beta* in degrees") + betar = property( + lambda self: self._betar, + doc="The reciprocal cell angle *beta* in degrees", + ) - gammar = property(lambda self: self._gammar, doc="The reciprocal cell angle *gamma* in degrees") + gammar = property( + lambda self: self._gammar, + doc="The reciprocal cell angle *gamma* in degrees", + ) - ca = property(lambda self: self._ca, doc="The cosine of the cell angle *alpha*.") + ca = property( + lambda self: self._ca, doc="The cosine of the cell angle *alpha*." + ) - cb = property(lambda self: self._cb, doc="The cosine of the cell angle *beta*.") + cb = property( + lambda self: self._cb, doc="The cosine of the cell angle *beta*." + ) - cg = property(lambda self: self._cg, doc="The cosine of the cell angle *gamma*.") + cg = property( + lambda self: self._cg, doc="The cosine of the cell angle *gamma*." + ) - sa = property(lambda self: self._sa, doc="The sine of the cell angle *alpha*.") + sa = property( + lambda self: self._sa, doc="The sine of the cell angle *alpha*." + ) - sb = property(lambda self: self._sb, doc="The sine of the cell angle *beta*.") + sb = property( + lambda self: self._sb, doc="The sine of the cell angle *beta*." + ) - sg = property(lambda self: self._sg, doc="The sine of the cell angle *gamma*.") + sg = property( + lambda self: self._sg, doc="The sine of the cell angle *gamma*." + ) - car = property(lambda self: self._car, doc="The cosine of the reciprocal angle *alpha*.") + car = property( + lambda self: self._car, + doc="The cosine of the reciprocal angle *alpha*.", + ) - cbr = property(lambda self: self._cbr, doc="The cosine of the reciprocal angle *beta*.") + cbr = property( + lambda self: self._cbr, + doc="The cosine of the reciprocal angle *beta*.", + ) - cgr = property(lambda self: self._cgr, doc="The cosine of the reciprocal angle *gamma*.") + cgr = property( + lambda self: self._cgr, + doc="The cosine of the reciprocal angle *gamma*.", + ) - sar = property(lambda self: self._sar, doc="The sine of the reciprocal angle *alpha*.") + sar = property( + lambda self: self._sar, doc="The sine of the reciprocal angle *alpha*." + ) - sbr = property(lambda self: self._sbr, doc="The sine of the reciprocal angle *beta*.") + sbr = property( + lambda self: self._sbr, doc="The sine of the reciprocal angle *beta*." + ) - sgr = property(lambda self: self._sgr, doc="The sine of the reciprocal angle *gamma*.") + sgr = property( + lambda self: self._sgr, doc="The sine of the reciprocal angle *gamma*." + ) # done with properties --------------------------------------------------- - def __init__(self, a=None, b=None, c=None, alpha=None, beta=None, gamma=None, baserot=None, base=None): + def __init__( + self, + a=None, + b=None, + c=None, + alpha=None, + beta=None, + gamma=None, + baserot=None, + base=None, + ): # build a set of provided argument names for later use. apairs = ( ("a", a), @@ -288,7 +361,16 @@ def __init__(self, a=None, b=None, c=None, alpha=None, beta=None, gamma=None, ba self.setLatPar(a, b, c, alpha, beta, gamma, baserot=baserot) return - def setLatPar(self, a=None, b=None, c=None, alpha=None, beta=None, gamma=None, baserot=None): + def setLatPar( + self, + a=None, + b=None, + c=None, + alpha=None, + beta=None, + gamma=None, + baserot=None, + ): """Set one or more lattice parameters. This updates all attributes that depend on the lattice parameters. @@ -362,7 +444,11 @@ def setLatPar(self, a=None, b=None, c=None, alpha=None, beta=None, gamma=None, b ) # standard Cartesian coordinates of lattice vectors self.stdbase = numpy.array( - [[1.0 / ar, -cgr / sgr / ar, cb * self.a], [0.0, self.b * sa, self.b * ca], [0.0, 0.0, self.c]], + [ + [1.0 / ar, -cgr / sgr / ar, cb * self.a], + [0.0, self.b * sa, self.b * ca], + [0.0, 0.0, self.c], + ], dtype=float, ) # Cartesian coordinates of lattice vectors @@ -424,7 +510,12 @@ def setLatBase(self, base): self._gammar = math.degrees(math.acos(cgr)) # standard orientation of lattice vectors self.stdbase = numpy.array( - [[1.0 / ar, -cgr / sgr / ar, cb * a], [0.0, b * sa, b * ca], [0.0, 0.0, c]], dtype=float + [ + [1.0 / ar, -cgr / sgr / ar, cb * a], + [0.0, b * sa, b * ca], + [0.0, 0.0, c], + ], + dtype=float, ) # calculate unit cell rotation matrix, base = stdbase @ baserot self.baserot = numpy.dot(numalg.inv(self.stdbase), self.base) @@ -435,7 +526,11 @@ def setLatBase(self, base): self.isotropicunit = _isotropicunit(self.recnormbase) # update metrics tensor self.metrics = numpy.array( - [[a * a, a * b * cg, a * c * cb], [b * a * cg, b * b, b * c * ca], [c * a * cb, c * b * ca, c * c]], + [ + [a * a, a * b * cg, a * c * cb], + [b * a * cg, b * b, b * c * ca], + [c * a * cb, c * b * ca, c * c], + ], dtype=float, ) return @@ -627,7 +722,10 @@ def __repr__(self): elif numpy.fabs(latpardiff).max() < self._epsilon: s = "Lattice()" else: - s = "Lattice(a=%g, b=%g, c=%g, alpha=%g, beta=%g, gamma=%g)" % self.abcABG() + s = ( + "Lattice(a=%g, b=%g, c=%g, alpha=%g, beta=%g, gamma=%g)" + % self.abcABG() + ) return s diff --git a/src/diffpy/structure/mmlibspacegroups.py b/src/diffpy/structure/mmlibspacegroups.py index faa5ce2..c3507f9 100644 --- a/src/diffpy/structure/mmlibspacegroups.py +++ b/src/diffpy/structure/mmlibspacegroups.py @@ -3,8 +3,7 @@ # This code is part of the PyMMLib distribution and governed by # its license.Please see the LICENSE_pymmlib file that should have been # included as part of this package. -"""Space groups defined as a part of the pymmlib. -""" +"""Space groups defined as a part of the pymmlib.""" from diffpy.structure.spacegroupmod import ( Rot_mX_mXY_mZ, @@ -3270,7 +3269,11 @@ point_group_name="PG3", crystal_system="TRIGONAL", pdb_name="P 3", - symop_list=[SymOp(Rot_X_Y_Z, Tr_0_0_0), SymOp(Rot_mY_XmY_Z, Tr_0_0_0), SymOp(Rot_mXY_mX_Z, Tr_0_0_0)], + symop_list=[ + SymOp(Rot_X_Y_Z, Tr_0_0_0), + SymOp(Rot_mY_XmY_Z, Tr_0_0_0), + SymOp(Rot_mXY_mX_Z, Tr_0_0_0), + ], ) sg144 = SpaceGroup( @@ -3281,7 +3284,11 @@ point_group_name="PG3", crystal_system="TRIGONAL", pdb_name="P 31", - symop_list=[SymOp(Rot_X_Y_Z, Tr_0_0_0), SymOp(Rot_mY_XmY_Z, Tr_0_0_13), SymOp(Rot_mXY_mX_Z, Tr_0_0_23)], + symop_list=[ + SymOp(Rot_X_Y_Z, Tr_0_0_0), + SymOp(Rot_mY_XmY_Z, Tr_0_0_13), + SymOp(Rot_mXY_mX_Z, Tr_0_0_23), + ], ) sg145 = SpaceGroup( @@ -3292,7 +3299,11 @@ point_group_name="PG3", crystal_system="TRIGONAL", pdb_name="P 32", - symop_list=[SymOp(Rot_X_Y_Z, Tr_0_0_0), SymOp(Rot_mY_XmY_Z, Tr_0_0_23), SymOp(Rot_mXY_mX_Z, Tr_0_0_13)], + symop_list=[ + SymOp(Rot_X_Y_Z, Tr_0_0_0), + SymOp(Rot_mY_XmY_Z, Tr_0_0_23), + SymOp(Rot_mXY_mX_Z, Tr_0_0_13), + ], ) sg146 = SpaceGroup( @@ -3324,7 +3335,11 @@ point_group_name="PG3", crystal_system="TRIGONAL", pdb_name="R 3", - symop_list=[SymOp(Rot_X_Y_Z, Tr_0_0_0), SymOp(Rot_Z_X_Y, Tr_0_0_0), SymOp(Rot_Y_Z_X, Tr_0_0_0)], + symop_list=[ + SymOp(Rot_X_Y_Z, Tr_0_0_0), + SymOp(Rot_Z_X_Y, Tr_0_0_0), + SymOp(Rot_Y_Z_X, Tr_0_0_0), + ], ) sg147 = SpaceGroup( diff --git a/src/diffpy/structure/parsers/__init__.py b/src/diffpy/structure/parsers/__init__.py index 0d549b8..de834ac 100644 --- a/src/diffpy/structure/parsers/__init__.py +++ b/src/diffpy/structure/parsers/__init__.py @@ -71,13 +71,17 @@ def getParser(format, **kw): def inputFormats(): """Return list of implemented input structure formats.""" - input_formats = [fmt for fmt, prop in parser_index.items() if prop["has_input"]] + input_formats = [ + fmt for fmt, prop in parser_index.items() if prop["has_input"] + ] input_formats.sort() return input_formats def outputFormats(): """Return list of implemented output structure formats.""" - output_formats = [fmt for fmt, prop in parser_index.items() if prop["has_output"]] + output_formats = [ + fmt for fmt, prop in parser_index.items() if prop["has_output"] + ] output_formats.sort() return output_formats diff --git a/src/diffpy/structure/parsers/p_auto.py b/src/diffpy/structure/parsers/p_auto.py index 745eb5a..2a199cf 100644 --- a/src/diffpy/structure/parsers/p_auto.py +++ b/src/diffpy/structure/parsers/p_auto.py @@ -188,7 +188,10 @@ def _wrapParseMethod(self, method, *args, **kwargs): pass if stru is None: emsg = "\n".join( - ["Unknown or invalid structure format.", "Errors per each tested structure format:"] + [ + "Unknown or invalid structure format.", + "Errors per each tested structure format:", + ] + parsers_emsgs ) raise StructureFormatError(emsg) diff --git a/src/diffpy/structure/parsers/p_cif.py b/src/diffpy/structure/parsers/p_cif.py index 6fba3b4..c34d254 100644 --- a/src/diffpy/structure/parsers/p_cif.py +++ b/src/diffpy/structure/parsers/p_cif.py @@ -482,7 +482,8 @@ def _parse_atom_site_label(self, block): # process _atom_site_label atom_site_loop = block.GetLoop("_atom_site_label") does_adp_type = ( - "_atom_site_adp_type" in atom_site_loop or "_atom_site_thermal_displace_type" in atom_site_loop + "_atom_site_adp_type" in atom_site_loop + or "_atom_site_thermal_displace_type" in atom_site_loop ) # get a list of setters for atom_site values prop_setters = P_cif._get_atom_setters(atom_site_loop) @@ -552,7 +553,10 @@ def _parse_space_group_symop_operation_xyz(self, block): from diffpy.structure.spacegroups import FindSpaceGroup, GetSpaceGroup, IsSpaceGroupIdentifier, SpaceGroup self.asymmetric_unit = list(self.stru) - sym_synonyms = ("_space_group_symop_operation_xyz", "_symmetry_equiv_pos_as_xyz") + sym_synonyms = ( + "_space_group_symop_operation_xyz", + "_symmetry_equiv_pos_as_xyz", + ) sym_loop_name = [n for n in sym_synonyms if n in block] # recover explicit list of symmetry operations symop_list = [] @@ -564,14 +568,20 @@ def _parse_space_group_symop_operation_xyz(self, block): opcif = getSymOp(eqxyz) symop_list.append(opcif) # determine space group number - sg_nameHall = block.get("_space_group_name_Hall", "") or block.get("_symmetry_space_group_name_Hall", "") + sg_nameHall = block.get("_space_group_name_Hall", "") or block.get( + "_symmetry_space_group_name_Hall", "" + ) sg_nameHM = ( block.get("_space_group_name_H-M_alt", "") or block.get("_space_group_name_H-M_ref", "") or block.get("_symmetry_space_group_name_H-M", "") ) self.cif_sgname = sg_nameHall or sg_nameHM or None - sgid = block.get("_space_group_IT_number", "") or block.get("_symmetry_Int_Tables_number", "") or sg_nameHM + sgid = ( + block.get("_space_group_IT_number", "") + or block.get("_symmetry_Int_Tables_number", "") + or sg_nameHM + ) self.spacegroup = None # try to reuse existing space group from symmetry operations if symop_list: @@ -587,10 +597,14 @@ def _parse_space_group_symop_operation_xyz(self, block): if symop_list and self.spacegroup is None: new_short_name = "CIF " + (sg_nameHall or "data") new_crystal_system = ( - block.get("_space_group_crystal_system") or block.get("_symmetry_cell_setting") or "TRICLINIC" + block.get("_space_group_crystal_system") + or block.get("_symmetry_cell_setting") + or "TRICLINIC" ).upper() self.spacegroup = SpaceGroup( - short_name=new_short_name, crystal_system=new_crystal_system, symop_list=symop_list + short_name=new_short_name, + crystal_system=new_crystal_system, + symop_list=symop_list, ) if self.spacegroup is None: emsg = "CIF file has unknown space group identifier {!r}." @@ -612,7 +626,9 @@ def _expandAsymmetricUnit(self, block): corepos = [a.xyz for a in self.stru] coreUijs = [a.U for a in self.stru] - self.eau = ExpandAsymmetricUnit(self.spacegroup, corepos, coreUijs, eps=self.eps) + self.eau = ExpandAsymmetricUnit( + self.spacegroup, corepos, coreUijs, eps=self.eps + ) # setup anisotropy according to symmetry requirements # unless it was already explicitly set for ca, uisotropy in zip(self.stru, self.eau.Uisotropy): @@ -691,7 +707,9 @@ def toLines(self, stru): a_site_label = [] a_adp_type = [] for a in stru: - cnt = element_count[a.element] = element_count.get(a.element, 0) + 1 + cnt = element_count[a.element] = ( + element_count.get(a.element, 0) + 1 + ) a_site_label.append("%s%i" % (a.element, cnt)) if numpy.all(a.U == a.U[0, 0] * numpy.identity(3)): a_adp_type.append("Uiso") diff --git a/src/diffpy/structure/parsers/p_discus.py b/src/diffpy/structure/parsers/p_discus.py index 3ee7e5f..e7fc54b 100644 --- a/src/diffpy/structure/parsers/p_discus.py +++ b/src/diffpy/structure/parsers/p_discus.py @@ -13,8 +13,7 @@ # ############################################################################## -"""Parser for DISCUS structure format -""" +"""Parser for DISCUS structure format""" import sys from functools import reduce @@ -117,12 +116,17 @@ def parseLines(self, lines): exp_natoms = reduce(lambda x, y: x * y, self.stru.pdffit["ncell"]) # only check if ncell record exists if self.ncell_read and exp_natoms != len(self.stru): - emsg = "Expected %d atoms, read %d." % (exp_natoms, len(self.stru)) + emsg = "Expected %d atoms, read %d." % ( + exp_natoms, + len(self.stru), + ) raise StructureFormatError(emsg) # take care of superlattice if self.stru.pdffit["ncell"][:3] != [1, 1, 1]: latpars = list(self.stru.lattice.abcABG()) - superlatpars = [latpars[i] * self.stru.pdffit["ncell"][i] for i in range(3)] + latpars[3:] + superlatpars = [ + latpars[i] * self.stru.pdffit["ncell"][i] for i in range(3) + ] + latpars[3:] superlattice = Lattice(*superlatpars) self.stru.placeInLattice(superlattice) self.stru.pdffit["ncell"] = [1, 1, 1, exp_natoms] @@ -165,12 +169,22 @@ def toLines(self, stru): if stru_pdffit.get("stepcut", 0.0) > 0.0: line = "shape stepcut, %g" % stru_pdffit["stepcut"] lines.append(line) - lines.append("cell %9.6f, %9.6f, %9.6f, %9.6f, %9.6f, %9.6f" % self.stru.lattice.abcABG()) + lines.append( + "cell %9.6f, %9.6f, %9.6f, %9.6f, %9.6f, %9.6f" + % self.stru.lattice.abcABG() + ) lines.append("ncell %9i, %9i, %9i, %9i" % (1, 1, 1, len(self.stru))) lines.append("atoms") for a in self.stru: lines.append( - "%-4s %17.8f %17.8f %17.8f %12.4f" % (a.element.upper(), a.xyz[0], a.xyz[1], a.xyz[2], a.Bisoequiv) + "%-4s %17.8f %17.8f %17.8f %12.4f" + % ( + a.element.upper(), + a.xyz[0], + a.xyz[1], + a.xyz[2], + a.Bisoequiv, + ) ) return lines @@ -195,7 +209,9 @@ def _parse_cell(self, words): try: self.stru.lattice.setLatPar(*latpars) except ZeroDivisionError: - emsg = "%d: Invalid lattice parameters - zero cell volume" % self.nl + emsg = ( + "%d: Invalid lattice parameters - zero cell volume" % self.nl + ) raise StructureFormatError(emsg) self.cell_read = True return @@ -292,7 +308,10 @@ def _parse_not_implemented(self, words): NotImplementedError If the record is not implemented. """ - emsg = "%d: reading of DISCUS record %r is not implemented." % (self.nl, words[0]) + emsg = "%d: reading of DISCUS record %r is not implemented." % ( + self.nl, + words[0], + ) raise NotImplementedError(emsg) diff --git a/src/diffpy/structure/parsers/p_pdb.py b/src/diffpy/structure/parsers/p_pdb.py index 6d0f95a..6f35eae 100644 --- a/src/diffpy/structure/parsers/p_pdb.py +++ b/src/diffpy/structure/parsers/p_pdb.py @@ -176,7 +176,10 @@ def parseLines(self, lines): abcABGscale = numpy.array(stru.lattice.abcABG()) reldiff = numpy.fabs(1.0 - abcABGscale / abcABGcryst) if not numpy.all(reldiff < 1.0e-4): - emsg = "%d: " % p_nl + "SCALE and CRYST1 are not consistent." + emsg = ( + "%d: " % p_nl + + "SCALE and CRYST1 are not consistent." + ) raise StructureFormatError(emsg) if numpy.any(scaleU != 0.0): emsg = "Origin offset not yet implemented." @@ -325,7 +328,19 @@ def atomLines(self, stru, idx): isotropic = numpy.all(a.U == a.U[0, 0] * numpy.identity(3)) if not isotropic: mid = " %7i%7i%7i%7i%7i%7i " % tuple( - numpy.around(1e4 * numpy.array([a.U[0, 0], a.U[1, 1], a.U[2, 2], a.U[0, 1], a.U[0, 2], a.U[1, 2]])) + numpy.around( + 1e4 + * numpy.array( + [ + a.U[0, 0], + a.U[1, 1], + a.U[2, 2], + a.U[0, 1], + a.U[0, 2], + a.U[1, 2], + ] + ) + ) ) line = "ANISOU" + atomline[6:27] + mid + atomline[72:80] lines.append(line) @@ -339,9 +354,9 @@ def atomLines(self, stru, idx): sigB = [8 * pi**2 * numpy.average([sigU[i, i] for i in range(3)])] sigmas = numpy.concatenate((sigxyz, sigo, sigB)) # no need to print sigmas if they all round to zero - hassigmas = numpy.any(numpy.fabs(sigmas) >= numpy.array(3 * [5e-4] + 2 * [5e-3])) or numpy.any( - numpy.fabs(sigU) > 5.0e-5 - ) + hassigmas = numpy.any( + numpy.fabs(sigmas) >= numpy.array(3 * [5e-4] + 2 * [5e-3]) + ) or numpy.any(numpy.fabs(sigU) > 5.0e-5) if hassigmas: mid = " %8.3f%8.3f%8.3f%6.2f%6.2f " % tuple(sigmas) line = "SIGATM" + atomline[6:27] + mid + atomline[72:80] @@ -350,7 +365,17 @@ def atomLines(self, stru, idx): if not numpy.all(sigU == sigU[0, 0] * numpy.identity(3)): mid = " %7i%7i%7i%7i%7i%7i " % tuple( numpy.around( - 1e4 * numpy.array([sigU[0, 0], sigU[1, 1], sigU[2, 2], sigU[0, 1], sigU[0, 2], sigU[1, 2]]) + 1e4 + * numpy.array( + [ + sigU[0, 0], + sigU[1, 1], + sigU[2, 2], + sigU[0, 1], + sigU[0, 2], + sigU[1, 2], + ] + ) ) ) line = "SIGUIJ" + atomline[6:27] + mid + atomline[72:80] @@ -383,7 +408,14 @@ def toLines(self, stru): + "%(resSeq)4i" # 23-26 + "%(iCode)c" # 27 + "%(blank)53s" # 28-80 - ) % {"serial": len(stru) + 1, "resName": "", "chainID": " ", "resSeq": 1, "iCode": " ", "blank": " "} + ) % { + "serial": len(stru) + 1, + "resName": "", + "chainID": " ", + "resSeq": 1, + "iCode": " ", + "blank": " ", + } lines.append(line) lines.append("%-80s" % "END") return lines diff --git a/src/diffpy/structure/parsers/p_pdffit.py b/src/diffpy/structure/parsers/p_pdffit.py index 692c417..7723a18 100644 --- a/src/diffpy/structure/parsers/p_pdffit.py +++ b/src/diffpy/structure/parsers/p_pdffit.py @@ -13,8 +13,7 @@ # ############################################################################## -"""Parser for PDFfit structure format -""" +"""Parser for PDFfit structure format""" import sys from functools import reduce @@ -169,7 +168,9 @@ def parseLines(self, lines): emsg = "expected %d atoms, read %d" % (p_natoms, len(stru)) raise StructureFormatError(emsg) if stru.pdffit["ncell"][:3] != [1, 1, 1]: - superlatpars = [latpars[i] * stru.pdffit["ncell"][i] for i in range(3)] + latpars[3:] + superlatpars = [ + latpars[i] * stru.pdffit["ncell"][i] for i in range(3) + ] + latpars[3:] superlattice = Lattice(*superlatpars) stru.placeInLattice(superlattice) stru.pdffit["ncell"] = [1, 1, 1, p_natoms] @@ -210,7 +211,12 @@ def toLines(self, stru): lines.append("scale %9.6f" % stru_pdffit["scale"]) lines.append( "sharp %9.6f, %9.6f, %9.6f, %9.6f" - % (stru_pdffit["delta2"], stru_pdffit["delta1"], stru_pdffit["sratio"], stru_pdffit["rcut"]) + % ( + stru_pdffit["delta2"], + stru_pdffit["delta1"], + stru_pdffit["sratio"], + stru_pdffit["rcut"], + ) ) lines.append("spcgr " + stru_pdffit["spcgr"]) if stru_pdffit.get("spdiameter", 0.0) > 0.0: @@ -224,15 +230,27 @@ def toLines(self, stru): "cell %9.6f, %9.6f, %9.6f, %9.6f, %9.6f, %9.6f" % (lat.a, lat.b, lat.c, lat.alpha, lat.beta, lat.gamma) ) - lines.append("dcell %9.6f, %9.6f, %9.6f, %9.6f, %9.6f, %9.6f" % tuple(stru_pdffit["dcell"])) + lines.append( + "dcell %9.6f, %9.6f, %9.6f, %9.6f, %9.6f, %9.6f" + % tuple(stru_pdffit["dcell"]) + ) lines.append("ncell %9i, %9i, %9i, %9i" % (1, 1, 1, len(stru))) lines.append("atoms") for a in stru: ad = a.__dict__ lines.append( - "%-4s %17.8f %17.8f %17.8f %12.4f" % (a.element.upper(), a.xyz[0], a.xyz[1], a.xyz[2], a.occupancy) + "%-4s %17.8f %17.8f %17.8f %12.4f" + % ( + a.element.upper(), + a.xyz[0], + a.xyz[1], + a.xyz[2], + a.occupancy, + ) + ) + sigmas = numpy.concatenate( + (ad.get("sigxyz", d_sigxyz), [ad.get("sigo", d_sigo)]) ) - sigmas = numpy.concatenate((ad.get("sigxyz", d_sigxyz), [ad.get("sigo", d_sigo)])) lines.append(" %18.8f %17.8f %17.8f %12.4f" % tuple(sigmas)) sigU = ad.get("sigU", d_sigU) Uii = (a.U[0][0], a.U[1][1], a.U[2][2]) diff --git a/src/diffpy/structure/parsers/p_rawxyz.py b/src/diffpy/structure/parsers/p_rawxyz.py index 65e9588..27e7613 100644 --- a/src/diffpy/structure/parsers/p_rawxyz.py +++ b/src/diffpy/structure/parsers/p_rawxyz.py @@ -81,7 +81,9 @@ def parseLines(self, lines): floatfields = [isfloat(f) for f in linefields[start]] nfields = len(linefields[start]) if nfields not in (3, 4): - emsg = "%d: invalid RAWXYZ format, expected 3 or 4 columns" % (start + 1) + emsg = "%d: invalid RAWXYZ format, expected 3 or 4 columns" % ( + start + 1 + ) raise StructureFormatError(emsg) if floatfields[:3] == [True, True, True]: el_idx, x_idx = (None, 0) @@ -98,7 +100,10 @@ def parseLines(self, lines): if fields == []: continue elif len(fields) != nfields: - emsg = ("%d: all lines must have " + "the same number of columns") % p_nl + emsg = ( + "%d: all lines must have " + + "the same number of columns" + ) % p_nl raise StructureFormatError(emsg) element = el_idx is not None and fields[el_idx] or "" xyz = [float(f) for f in fields[x_idx : x_idx + 3]] diff --git a/src/diffpy/structure/parsers/p_xcfg.py b/src/diffpy/structure/parsers/p_xcfg.py index 372e7ba..651fec4 100644 --- a/src/diffpy/structure/parsers/p_xcfg.py +++ b/src/diffpy/structure/parsers/p_xcfg.py @@ -218,7 +218,10 @@ def parseLines(self, lines): continue elif xcfg_Number_of_particles is None: if line.find("Number of particles =") != 0: - emsg = ("%d: first line must " + "contain 'Number of particles ='") % p_nl + emsg = ( + "%d: first line must " + + "contain 'Number of particles ='" + ) % p_nl raise StructureFormatError(emsg) xcfg_Number_of_particles = int(line[21:].split(None, 1)[0]) p_natoms = xcfg_Number_of_particles @@ -248,10 +251,15 @@ def parseLines(self, lines): p_auxiliary[i] = "aux%d" % i sorted_aux_keys = sorted(p_auxiliary.keys()) if p_auxnum != 0: - stru.xcfg = {"auxiliaries": [p_auxiliary[k] for k in sorted_aux_keys]} + stru.xcfg = { + "auxiliaries": [p_auxiliary[k] for k in sorted_aux_keys] + } ecnt = len(p_auxiliary) + (3 if xcfg_NO_VELOCITY else 6) if ecnt != xcfg_entry_count: - emsg = ("%d: auxiliary fields are " "not consistent with entry_count") % p_nl + emsg = ( + "%d: auxiliary fields are " + "not consistent with entry_count" + ) % p_nl raise StructureFormatError(emsg) # define proper lattice stru.lattice.setLatBase(xcfg_H0) @@ -272,7 +280,12 @@ def parseLines(self, lines): xyz = [xcfg_A * xi for xi in fields[:3]] stru.addNewAtom(p_element, xyz=xyz) a = stru[-1] - _assign_auxiliaries(a, fields, auxiliaries=p_auxiliary, no_velocity=xcfg_NO_VELOCITY) + _assign_auxiliaries( + a, + fields, + auxiliaries=p_auxiliary, + no_velocity=xcfg_NO_VELOCITY, + ) else: emsg = "%d: invalid record" % p_nl raise StructureFormatError(emsg) @@ -319,19 +332,28 @@ def toLines(self, stru): # range of CFG coordinates must be less than 1 p_A = numpy.ceil(max_range_xyz + 1.0e-13) # atomeye draws rubbish when boxsize is less than 3.5 - hi_ucvect = max([numpy.sqrt(numpy.dot(v, v)) for v in stru.lattice.base]) + hi_ucvect = max( + [numpy.sqrt(numpy.dot(v, v)) for v in stru.lattice.base] + ) if hi_ucvect * p_A < 3.5: p_A = numpy.ceil(3.5 / hi_ucvect) lines.append("A = %.8g Angstrom" % p_A) # how much do we need to shift the coordinates? p_dxyz = numpy.zeros(3, dtype=float) for i in range(3): - if lo_xyz[i] / p_A < 0.0 or hi_xyz[i] / p_A >= 1.0 or (lo_xyz[i] == hi_xyz[i] and lo_xyz[i] == 0.0): + if ( + lo_xyz[i] / p_A < 0.0 + or hi_xyz[i] / p_A >= 1.0 + or (lo_xyz[i] == hi_xyz[i] and lo_xyz[i] == 0.0) + ): p_dxyz[i] = 0.5 - (hi_xyz[i] + lo_xyz[i]) / 2.0 / p_A # H0 tensor for i in range(3): for j in range(3): - lines.append("H0(%i,%i) = %.8g A" % (i + 1, j + 1, stru.lattice.base[i, j])) + lines.append( + "H0(%i,%i) = %.8g A" + % (i + 1, j + 1, stru.lattice.base[i, j]) + ) # get out for empty structure if len(stru) == 0: return lines @@ -343,7 +365,9 @@ def toLines(self, stru): # if stru came from xcfg file, it would store original auxiliaries in # xcfg dictionary try: - p_auxiliaries = [(aux, "a." + aux) for aux in stru.xcfg["auxiliaries"]] + p_auxiliaries = [ + (aux, "a." + aux) for aux in stru.xcfg["auxiliaries"] + ] except AttributeError: p_auxiliaries = [] # add occupancy if any atom has nonunit occupancy @@ -367,7 +391,9 @@ def toLines(self, stru): elif p_allUiso: p_auxiliaries.append(("Uiso", "uflat[0]")) else: - p_auxiliaries.extend([("U11", "uflat[0]"), ("U22", "uflat[4]"), ("U33", "uflat[8]")]) + p_auxiliaries.extend( + [("U11", "uflat[0]"), ("U22", "uflat[4]"), ("U33", "uflat[8]")] + ) # check if there are off-diagonal elements allU = numpy.array([a.U for a in stru]) if numpy.any(allU[:, 0, 1] != 0.0): diff --git a/src/diffpy/structure/parsers/p_xyz.py b/src/diffpy/structure/parsers/p_xyz.py index cd540a9..25fecac 100644 --- a/src/diffpy/structure/parsers/p_xyz.py +++ b/src/diffpy/structure/parsers/p_xyz.py @@ -15,9 +15,9 @@ """Parser for XYZ file format, where - * First line gives number of atoms. - * Second line has optional title. - * Remaining lines contain element, `x, y, z`. +* First line gives number of atoms. +* Second line has optional title. +* Remaining lines contain element, `x, y, z`. """ import sys @@ -78,11 +78,15 @@ def parseLines(self, lines): stru.title = lines[start + 1].strip() start += 2 else: - emsg = "%d: invalid XYZ format, missing number of atoms" % (start + 1) + emsg = "%d: invalid XYZ format, missing number of atoms" % ( + start + 1 + ) raise StructureFormatError(emsg) except (IndexError, ValueError): exc_type, exc_value, exc_traceback = sys.exc_info() - emsg = "%d: invalid XYZ format, missing number of atoms" % (start + 1) + emsg = "%d: invalid XYZ format, missing number of atoms" % ( + start + 1 + ) e = StructureFormatError(emsg) raise e.with_traceback(exc_traceback) # find the last valid record @@ -105,7 +109,10 @@ def parseLines(self, lines): if fields == []: continue elif len(fields) != nfields: - emsg = ("%d: all lines must have " + "the same number of columns") % p_nl + emsg = ( + "%d: all lines must have " + + "the same number of columns" + ) % p_nl raise StructureFormatError(emsg) element = fields[0] element = element[0].upper() + element[1:].lower() diff --git a/src/diffpy/structure/parsers/structureparser.py b/src/diffpy/structure/parsers/structureparser.py index 2b74866..83cf18c 100644 --- a/src/diffpy/structure/parsers/structureparser.py +++ b/src/diffpy/structure/parsers/structureparser.py @@ -13,8 +13,7 @@ # ############################################################################## -"""Definition of StructureParser, a base class for specific parsers. -""" +"""Definition of StructureParser, a base class for specific parsers.""" class StructureParser(object): @@ -42,7 +41,9 @@ def parseLines(self, lines): ---- This method has to be overloaded in derived class. """ - raise NotImplementedError("parseLines not defined for '%s' format" % self.format) + raise NotImplementedError( + "parseLines not defined for '%s' format" % self.format + ) return def toLines(self, stru): @@ -54,7 +55,9 @@ def toLines(self, stru): ---- This method has to be overloaded in derived class. """ - raise NotImplementedError("toLines not defined for '%s' format" % self.format) + raise NotImplementedError( + "toLines not defined for '%s' format" % self.format + ) def parse(self, s): """Create `Structure` instance from a string.""" diff --git a/src/diffpy/structure/pdffitstructure.py b/src/diffpy/structure/pdffitstructure.py index cc3b66d..414b10b 100644 --- a/src/diffpy/structure/pdffitstructure.py +++ b/src/diffpy/structure/pdffitstructure.py @@ -13,8 +13,7 @@ # ############################################################################## -"""Definition of PDFFitStructure class derived from Structure -""" +"""Definition of PDFFitStructure class derived from Structure""" from diffpy.structure.structure import Structure diff --git a/src/diffpy/structure/spacegroupmod.py b/src/diffpy/structure/spacegroupmod.py index c31b7ca..f608f23 100644 --- a/src/diffpy/structure/spacegroupmod.py +++ b/src/diffpy/structure/spacegroupmod.py @@ -3,76 +3,203 @@ # This code is part of the PyMMLib distribution and governed by # its license. Please see the LICENSE_pymmlib file that should have been # included as part of this package. -"""Symmetry operations as functions on vectors or arrays. -""" +"""Symmetry operations as functions on vectors or arrays.""" import numpy # 64 unique rotation matricies -Rot_Z_mY_X = numpy.array([[0.0, 0.0, 1.0], [0.0, -1.0, 0.0], [1.0, 0.0, 0.0]], float) -Rot_Y_mX_mZ = numpy.array([[0.0, 1.0, 0.0], [-1.0, 0.0, 0.0], [0.0, 0.0, -1.0]], float) -Rot_XmY_X_mZ = numpy.array([[1.0, -1.0, 0.0], [1.0, 0.0, 0.0], [0.0, 0.0, -1.0]], float) -Rot_mX_Y_mZ = numpy.array([[-1.0, 0.0, 0.0], [0.0, 1.0, 0.0], [0.0, 0.0, -1.0]], float) -Rot_X_mZ_Y = numpy.array([[1.0, 0.0, 0.0], [0.0, 0.0, -1.0], [0.0, 1.0, 0.0]], float) -Rot_Y_mXY_Z = numpy.array([[0.0, 1.0, 0.0], [-1.0, 1.0, 0.0], [0.0, 0.0, 1.0]], float) -Rot_Y_mX_Z = numpy.array([[0.0, 1.0, 0.0], [-1.0, 0.0, 0.0], [0.0, 0.0, 1.0]], float) -Rot_XmY_X_Z = numpy.array([[1.0, -1.0, 0.0], [1.0, 0.0, 0.0], [0.0, 0.0, 1.0]], float) -Rot_mX_mXY_mZ = numpy.array([[-1.0, 0.0, 0.0], [-1.0, 1.0, 0.0], [0.0, 0.0, -1.0]], float) -Rot_Y_Z_X = numpy.array([[0.0, 1.0, 0.0], [0.0, 0.0, 1.0], [1.0, 0.0, 0.0]], float) -Rot_mY_mZ_X = numpy.array([[0.0, -1.0, 0.0], [0.0, 0.0, -1.0], [1.0, 0.0, 0.0]], float) -Rot_X_Z_mY = numpy.array([[1.0, 0.0, 0.0], [0.0, 0.0, 1.0], [0.0, -1.0, 0.0]], float) -Rot_XmY_mY_Z = numpy.array([[1.0, -1.0, 0.0], [0.0, -1.0, 0.0], [0.0, 0.0, 1.0]], float) -Rot_Y_X_mZ = numpy.array([[0.0, 1.0, 0.0], [1.0, 0.0, 0.0], [0.0, 0.0, -1.0]], float) -Rot_Y_mZ_X = numpy.array([[0.0, 1.0, 0.0], [0.0, 0.0, -1.0], [1.0, 0.0, 0.0]], float) -Rot_mXY_Y_Z = numpy.array([[-1.0, 1.0, 0.0], [0.0, 1.0, 0.0], [0.0, 0.0, 1.0]], float) -Rot_mX_mY_mZ = numpy.array([[-1.0, 0.0, 0.0], [0.0, -1.0, 0.0], [0.0, 0.0, -1.0]], float) -Rot_X_Y_mZ = numpy.array([[1.0, 0.0, 0.0], [0.0, 1.0, 0.0], [0.0, 0.0, -1.0]], float) -Rot_mXY_mX_Z = numpy.array([[-1.0, 1.0, 0.0], [-1.0, 0.0, 0.0], [0.0, 0.0, 1.0]], float) -Rot_mZ_mY_mX = numpy.array([[0.0, 0.0, -1.0], [0.0, -1.0, 0.0], [-1.0, 0.0, 0.0]], float) -Rot_X_mZ_mY = numpy.array([[1.0, 0.0, 0.0], [0.0, 0.0, -1.0], [0.0, -1.0, 0.0]], float) -Rot_X_Y_Z = numpy.array([[1.0, 0.0, 0.0], [0.0, 1.0, 0.0], [0.0, 0.0, 1.0]], float) -Rot_mY_mX_mZ = numpy.array([[0.0, -1.0, 0.0], [-1.0, 0.0, 0.0], [0.0, 0.0, -1.0]], float) -Rot_mY_X_Z = numpy.array([[0.0, -1.0, 0.0], [1.0, 0.0, 0.0], [0.0, 0.0, 1.0]], float) -Rot_Z_X_Y = numpy.array([[0.0, 0.0, 1.0], [1.0, 0.0, 0.0], [0.0, 1.0, 0.0]], float) -Rot_X_XmY_Z = numpy.array([[1.0, 0.0, 0.0], [1.0, -1.0, 0.0], [0.0, 0.0, 1.0]], float) -Rot_mY_X_mZ = numpy.array([[0.0, -1.0, 0.0], [1.0, 0.0, 0.0], [0.0, 0.0, -1.0]], float) -Rot_mY_Z_mX = numpy.array([[0.0, -1.0, 0.0], [0.0, 0.0, 1.0], [-1.0, 0.0, 0.0]], float) -Rot_mY_Z_X = numpy.array([[0.0, -1.0, 0.0], [0.0, 0.0, 1.0], [1.0, 0.0, 0.0]], float) -Rot_mX_mZ_mY = numpy.array([[-1.0, 0.0, 0.0], [0.0, 0.0, -1.0], [0.0, -1.0, 0.0]], float) -Rot_mX_Z_Y = numpy.array([[-1.0, 0.0, 0.0], [0.0, 0.0, 1.0], [0.0, 1.0, 0.0]], float) -Rot_mZ_mX_mY = numpy.array([[0.0, 0.0, -1.0], [-1.0, 0.0, 0.0], [0.0, -1.0, 0.0]], float) -Rot_X_XmY_mZ = numpy.array([[1.0, 0.0, 0.0], [1.0, -1.0, 0.0], [0.0, 0.0, -1.0]], float) -Rot_mY_XmY_mZ = numpy.array([[0.0, -1.0, 0.0], [1.0, -1.0, 0.0], [0.0, 0.0, -1.0]], float) -Rot_Z_X_mY = numpy.array([[0.0, 0.0, 1.0], [1.0, 0.0, 0.0], [0.0, -1.0, 0.0]], float) -Rot_mZ_mY_X = numpy.array([[0.0, 0.0, -1.0], [0.0, -1.0, 0.0], [1.0, 0.0, 0.0]], float) -Rot_X_Z_Y = numpy.array([[1.0, 0.0, 0.0], [0.0, 0.0, 1.0], [0.0, 1.0, 0.0]], float) -Rot_Z_mX_mY = numpy.array([[0.0, 0.0, 1.0], [-1.0, 0.0, 0.0], [0.0, -1.0, 0.0]], float) -Rot_mX_Z_mY = numpy.array([[-1.0, 0.0, 0.0], [0.0, 0.0, 1.0], [0.0, -1.0, 0.0]], float) -Rot_X_mY_Z = numpy.array([[1.0, 0.0, 0.0], [0.0, -1.0, 0.0], [0.0, 0.0, 1.0]], float) -Rot_mY_mX_Z = numpy.array([[0.0, -1.0, 0.0], [-1.0, 0.0, 0.0], [0.0, 0.0, 1.0]], float) -Rot_Z_mY_mX = numpy.array([[0.0, 0.0, 1.0], [0.0, -1.0, 0.0], [-1.0, 0.0, 0.0]], float) -Rot_mX_mY_Z = numpy.array([[-1.0, 0.0, 0.0], [0.0, -1.0, 0.0], [0.0, 0.0, 1.0]], float) -Rot_Z_Y_X = numpy.array([[0.0, 0.0, 1.0], [0.0, 1.0, 0.0], [1.0, 0.0, 0.0]], float) -Rot_mZ_Y_mX = numpy.array([[0.0, 0.0, -1.0], [0.0, 1.0, 0.0], [-1.0, 0.0, 0.0]], float) -Rot_Y_Z_mX = numpy.array([[0.0, 1.0, 0.0], [0.0, 0.0, 1.0], [-1.0, 0.0, 0.0]], float) -Rot_mY_XmY_Z = numpy.array([[0.0, -1.0, 0.0], [1.0, -1.0, 0.0], [0.0, 0.0, 1.0]], float) -Rot_mXY_Y_mZ = numpy.array([[-1.0, 1.0, 0.0], [0.0, 1.0, 0.0], [0.0, 0.0, -1.0]], float) -Rot_mZ_mX_Y = numpy.array([[0.0, 0.0, -1.0], [-1.0, 0.0, 0.0], [0.0, 1.0, 0.0]], float) -Rot_mX_mZ_Y = numpy.array([[-1.0, 0.0, 0.0], [0.0, 0.0, -1.0], [0.0, 1.0, 0.0]], float) -Rot_mX_Y_Z = numpy.array([[-1.0, 0.0, 0.0], [0.0, 1.0, 0.0], [0.0, 0.0, 1.0]], float) -Rot_X_mY_mZ = numpy.array([[1.0, 0.0, 0.0], [0.0, -1.0, 0.0], [0.0, 0.0, -1.0]], float) -Rot_mZ_X_Y = numpy.array([[0.0, 0.0, -1.0], [1.0, 0.0, 0.0], [0.0, 1.0, 0.0]], float) -Rot_Y_mZ_mX = numpy.array([[0.0, 1.0, 0.0], [0.0, 0.0, -1.0], [-1.0, 0.0, 0.0]], float) -Rot_mY_mZ_mX = numpy.array([[0.0, -1.0, 0.0], [0.0, 0.0, -1.0], [-1.0, 0.0, 0.0]], float) -Rot_mZ_Y_X = numpy.array([[0.0, 0.0, -1.0], [0.0, 1.0, 0.0], [1.0, 0.0, 0.0]], float) -Rot_Z_Y_mX = numpy.array([[0.0, 0.0, 1.0], [0.0, 1.0, 0.0], [-1.0, 0.0, 0.0]], float) -Rot_mXY_mX_mZ = numpy.array([[-1.0, 1.0, 0.0], [-1.0, 0.0, 0.0], [0.0, 0.0, -1.0]], float) -Rot_XmY_mY_mZ = numpy.array([[1.0, -1.0, 0.0], [0.0, -1.0, 0.0], [0.0, 0.0, -1.0]], float) -Rot_Z_mX_Y = numpy.array([[0.0, 0.0, 1.0], [-1.0, 0.0, 0.0], [0.0, 1.0, 0.0]], float) -Rot_mX_mXY_Z = numpy.array([[-1.0, 0.0, 0.0], [-1.0, 1.0, 0.0], [0.0, 0.0, 1.0]], float) -Rot_Y_mXY_mZ = numpy.array([[0.0, 1.0, 0.0], [-1.0, 1.0, 0.0], [0.0, 0.0, -1.0]], float) -Rot_mZ_X_mY = numpy.array([[0.0, 0.0, -1.0], [1.0, 0.0, 0.0], [0.0, -1.0, 0.0]], float) -Rot_Y_X_Z = numpy.array([[0.0, 1.0, 0.0], [1.0, 0.0, 0.0], [0.0, 0.0, 1.0]], float) +Rot_Z_mY_X = numpy.array( + [[0.0, 0.0, 1.0], [0.0, -1.0, 0.0], [1.0, 0.0, 0.0]], float +) +Rot_Y_mX_mZ = numpy.array( + [[0.0, 1.0, 0.0], [-1.0, 0.0, 0.0], [0.0, 0.0, -1.0]], float +) +Rot_XmY_X_mZ = numpy.array( + [[1.0, -1.0, 0.0], [1.0, 0.0, 0.0], [0.0, 0.0, -1.0]], float +) +Rot_mX_Y_mZ = numpy.array( + [[-1.0, 0.0, 0.0], [0.0, 1.0, 0.0], [0.0, 0.0, -1.0]], float +) +Rot_X_mZ_Y = numpy.array( + [[1.0, 0.0, 0.0], [0.0, 0.0, -1.0], [0.0, 1.0, 0.0]], float +) +Rot_Y_mXY_Z = numpy.array( + [[0.0, 1.0, 0.0], [-1.0, 1.0, 0.0], [0.0, 0.0, 1.0]], float +) +Rot_Y_mX_Z = numpy.array( + [[0.0, 1.0, 0.0], [-1.0, 0.0, 0.0], [0.0, 0.0, 1.0]], float +) +Rot_XmY_X_Z = numpy.array( + [[1.0, -1.0, 0.0], [1.0, 0.0, 0.0], [0.0, 0.0, 1.0]], float +) +Rot_mX_mXY_mZ = numpy.array( + [[-1.0, 0.0, 0.0], [-1.0, 1.0, 0.0], [0.0, 0.0, -1.0]], float +) +Rot_Y_Z_X = numpy.array( + [[0.0, 1.0, 0.0], [0.0, 0.0, 1.0], [1.0, 0.0, 0.0]], float +) +Rot_mY_mZ_X = numpy.array( + [[0.0, -1.0, 0.0], [0.0, 0.0, -1.0], [1.0, 0.0, 0.0]], float +) +Rot_X_Z_mY = numpy.array( + [[1.0, 0.0, 0.0], [0.0, 0.0, 1.0], [0.0, -1.0, 0.0]], float +) +Rot_XmY_mY_Z = numpy.array( + [[1.0, -1.0, 0.0], [0.0, -1.0, 0.0], [0.0, 0.0, 1.0]], float +) +Rot_Y_X_mZ = numpy.array( + [[0.0, 1.0, 0.0], [1.0, 0.0, 0.0], [0.0, 0.0, -1.0]], float +) +Rot_Y_mZ_X = numpy.array( + [[0.0, 1.0, 0.0], [0.0, 0.0, -1.0], [1.0, 0.0, 0.0]], float +) +Rot_mXY_Y_Z = numpy.array( + [[-1.0, 1.0, 0.0], [0.0, 1.0, 0.0], [0.0, 0.0, 1.0]], float +) +Rot_mX_mY_mZ = numpy.array( + [[-1.0, 0.0, 0.0], [0.0, -1.0, 0.0], [0.0, 0.0, -1.0]], float +) +Rot_X_Y_mZ = numpy.array( + [[1.0, 0.0, 0.0], [0.0, 1.0, 0.0], [0.0, 0.0, -1.0]], float +) +Rot_mXY_mX_Z = numpy.array( + [[-1.0, 1.0, 0.0], [-1.0, 0.0, 0.0], [0.0, 0.0, 1.0]], float +) +Rot_mZ_mY_mX = numpy.array( + [[0.0, 0.0, -1.0], [0.0, -1.0, 0.0], [-1.0, 0.0, 0.0]], float +) +Rot_X_mZ_mY = numpy.array( + [[1.0, 0.0, 0.0], [0.0, 0.0, -1.0], [0.0, -1.0, 0.0]], float +) +Rot_X_Y_Z = numpy.array( + [[1.0, 0.0, 0.0], [0.0, 1.0, 0.0], [0.0, 0.0, 1.0]], float +) +Rot_mY_mX_mZ = numpy.array( + [[0.0, -1.0, 0.0], [-1.0, 0.0, 0.0], [0.0, 0.0, -1.0]], float +) +Rot_mY_X_Z = numpy.array( + [[0.0, -1.0, 0.0], [1.0, 0.0, 0.0], [0.0, 0.0, 1.0]], float +) +Rot_Z_X_Y = numpy.array( + [[0.0, 0.0, 1.0], [1.0, 0.0, 0.0], [0.0, 1.0, 0.0]], float +) +Rot_X_XmY_Z = numpy.array( + [[1.0, 0.0, 0.0], [1.0, -1.0, 0.0], [0.0, 0.0, 1.0]], float +) +Rot_mY_X_mZ = numpy.array( + [[0.0, -1.0, 0.0], [1.0, 0.0, 0.0], [0.0, 0.0, -1.0]], float +) +Rot_mY_Z_mX = numpy.array( + [[0.0, -1.0, 0.0], [0.0, 0.0, 1.0], [-1.0, 0.0, 0.0]], float +) +Rot_mY_Z_X = numpy.array( + [[0.0, -1.0, 0.0], [0.0, 0.0, 1.0], [1.0, 0.0, 0.0]], float +) +Rot_mX_mZ_mY = numpy.array( + [[-1.0, 0.0, 0.0], [0.0, 0.0, -1.0], [0.0, -1.0, 0.0]], float +) +Rot_mX_Z_Y = numpy.array( + [[-1.0, 0.0, 0.0], [0.0, 0.0, 1.0], [0.0, 1.0, 0.0]], float +) +Rot_mZ_mX_mY = numpy.array( + [[0.0, 0.0, -1.0], [-1.0, 0.0, 0.0], [0.0, -1.0, 0.0]], float +) +Rot_X_XmY_mZ = numpy.array( + [[1.0, 0.0, 0.0], [1.0, -1.0, 0.0], [0.0, 0.0, -1.0]], float +) +Rot_mY_XmY_mZ = numpy.array( + [[0.0, -1.0, 0.0], [1.0, -1.0, 0.0], [0.0, 0.0, -1.0]], float +) +Rot_Z_X_mY = numpy.array( + [[0.0, 0.0, 1.0], [1.0, 0.0, 0.0], [0.0, -1.0, 0.0]], float +) +Rot_mZ_mY_X = numpy.array( + [[0.0, 0.0, -1.0], [0.0, -1.0, 0.0], [1.0, 0.0, 0.0]], float +) +Rot_X_Z_Y = numpy.array( + [[1.0, 0.0, 0.0], [0.0, 0.0, 1.0], [0.0, 1.0, 0.0]], float +) +Rot_Z_mX_mY = numpy.array( + [[0.0, 0.0, 1.0], [-1.0, 0.0, 0.0], [0.0, -1.0, 0.0]], float +) +Rot_mX_Z_mY = numpy.array( + [[-1.0, 0.0, 0.0], [0.0, 0.0, 1.0], [0.0, -1.0, 0.0]], float +) +Rot_X_mY_Z = numpy.array( + [[1.0, 0.0, 0.0], [0.0, -1.0, 0.0], [0.0, 0.0, 1.0]], float +) +Rot_mY_mX_Z = numpy.array( + [[0.0, -1.0, 0.0], [-1.0, 0.0, 0.0], [0.0, 0.0, 1.0]], float +) +Rot_Z_mY_mX = numpy.array( + [[0.0, 0.0, 1.0], [0.0, -1.0, 0.0], [-1.0, 0.0, 0.0]], float +) +Rot_mX_mY_Z = numpy.array( + [[-1.0, 0.0, 0.0], [0.0, -1.0, 0.0], [0.0, 0.0, 1.0]], float +) +Rot_Z_Y_X = numpy.array( + [[0.0, 0.0, 1.0], [0.0, 1.0, 0.0], [1.0, 0.0, 0.0]], float +) +Rot_mZ_Y_mX = numpy.array( + [[0.0, 0.0, -1.0], [0.0, 1.0, 0.0], [-1.0, 0.0, 0.0]], float +) +Rot_Y_Z_mX = numpy.array( + [[0.0, 1.0, 0.0], [0.0, 0.0, 1.0], [-1.0, 0.0, 0.0]], float +) +Rot_mY_XmY_Z = numpy.array( + [[0.0, -1.0, 0.0], [1.0, -1.0, 0.0], [0.0, 0.0, 1.0]], float +) +Rot_mXY_Y_mZ = numpy.array( + [[-1.0, 1.0, 0.0], [0.0, 1.0, 0.0], [0.0, 0.0, -1.0]], float +) +Rot_mZ_mX_Y = numpy.array( + [[0.0, 0.0, -1.0], [-1.0, 0.0, 0.0], [0.0, 1.0, 0.0]], float +) +Rot_mX_mZ_Y = numpy.array( + [[-1.0, 0.0, 0.0], [0.0, 0.0, -1.0], [0.0, 1.0, 0.0]], float +) +Rot_mX_Y_Z = numpy.array( + [[-1.0, 0.0, 0.0], [0.0, 1.0, 0.0], [0.0, 0.0, 1.0]], float +) +Rot_X_mY_mZ = numpy.array( + [[1.0, 0.0, 0.0], [0.0, -1.0, 0.0], [0.0, 0.0, -1.0]], float +) +Rot_mZ_X_Y = numpy.array( + [[0.0, 0.0, -1.0], [1.0, 0.0, 0.0], [0.0, 1.0, 0.0]], float +) +Rot_Y_mZ_mX = numpy.array( + [[0.0, 1.0, 0.0], [0.0, 0.0, -1.0], [-1.0, 0.0, 0.0]], float +) +Rot_mY_mZ_mX = numpy.array( + [[0.0, -1.0, 0.0], [0.0, 0.0, -1.0], [-1.0, 0.0, 0.0]], float +) +Rot_mZ_Y_X = numpy.array( + [[0.0, 0.0, -1.0], [0.0, 1.0, 0.0], [1.0, 0.0, 0.0]], float +) +Rot_Z_Y_mX = numpy.array( + [[0.0, 0.0, 1.0], [0.0, 1.0, 0.0], [-1.0, 0.0, 0.0]], float +) +Rot_mXY_mX_mZ = numpy.array( + [[-1.0, 1.0, 0.0], [-1.0, 0.0, 0.0], [0.0, 0.0, -1.0]], float +) +Rot_XmY_mY_mZ = numpy.array( + [[1.0, -1.0, 0.0], [0.0, -1.0, 0.0], [0.0, 0.0, -1.0]], float +) +Rot_Z_mX_Y = numpy.array( + [[0.0, 0.0, 1.0], [-1.0, 0.0, 0.0], [0.0, 1.0, 0.0]], float +) +Rot_mX_mXY_Z = numpy.array( + [[-1.0, 0.0, 0.0], [-1.0, 1.0, 0.0], [0.0, 0.0, 1.0]], float +) +Rot_Y_mXY_mZ = numpy.array( + [[0.0, 1.0, 0.0], [-1.0, 1.0, 0.0], [0.0, 0.0, -1.0]], float +) +Rot_mZ_X_mY = numpy.array( + [[0.0, 0.0, -1.0], [1.0, 0.0, 0.0], [0.0, -1.0, 0.0]], float +) +Rot_Y_X_Z = numpy.array( + [[0.0, 1.0, 0.0], [1.0, 0.0, 0.0], [0.0, 0.0, 1.0]], float +) # 32 unique translation vectors Tr_0_0_34 = numpy.array([0.0, 0.0, 3.0 / 4.0], float) @@ -138,9 +265,24 @@ def __init__(self, R, t): def __str__(self): """Printable representation of this SymOp object.""" - x = "[%6.3f %6.3f %6.3f %6.3f]\n" % (self.R[0, 0], self.R[0, 1], self.R[0, 2], self.t[0]) - x += "[%6.3f %6.3f %6.3f %6.3f]\n" % (self.R[1, 0], self.R[1, 1], self.R[1, 2], self.t[1]) - x += "[%6.3f %6.3f %6.3f %6.3f]\n" % (self.R[2, 0], self.R[2, 1], self.R[2, 2], self.t[2]) + x = "[%6.3f %6.3f %6.3f %6.3f]\n" % ( + self.R[0, 0], + self.R[0, 1], + self.R[0, 2], + self.t[0], + ) + x += "[%6.3f %6.3f %6.3f %6.3f]\n" % ( + self.R[1, 0], + self.R[1, 1], + self.R[1, 2], + self.t[1], + ) + x += "[%6.3f %6.3f %6.3f %6.3f]\n" % ( + self.R[2, 0], + self.R[2, 1], + self.R[2, 2], + self.t[2], + ) return x def __call__(self, vec): @@ -164,7 +306,9 @@ def __eq__(self, symop): Return ``True`` when *self* and *symop* difference is within tiny round-off errors. """ - return numpy.allclose(self.R, symop.R) and numpy.allclose(self.t, symop.t) + return numpy.allclose(self.R, symop.R) and numpy.allclose( + self.t, symop.t + ) def is_identity(self): """Check if this SymOp is an identity operation. @@ -175,7 +319,9 @@ def is_identity(self): ``True`` if this is an identity operation within a small round-off. Return ``False`` otherwise. """ - rv = numpy.allclose(self.R, numpy.identity(3, float)) and numpy.allclose(self.t, numpy.zeros(3, float)) + rv = numpy.allclose( + self.R, numpy.identity(3, float) + ) and numpy.allclose(self.t, numpy.zeros(3, float)) return rv @@ -257,7 +403,10 @@ def __init__( def __repr__(self): """Return a string representation of the space group.""" - return ("SpaceGroup #%i (%s, %s). Symmetry matrices: %i, " "point sym. matr.: %i") % ( + return ( + "SpaceGroup #%i (%s, %s). Symmetry matrices: %i, " + "point sym. matr.: %i" + ) % ( self.number, self.short_name, self.crystal_system[0] + self.crystal_system[1:].lower(), diff --git a/src/diffpy/structure/structure.py b/src/diffpy/structure/structure.py index f0cb515..8939f7a 100644 --- a/src/diffpy/structure/structure.py +++ b/src/diffpy/structure/structure.py @@ -13,8 +13,7 @@ # ############################################################################## -"""This module defines class `Structure`. -""" +"""This module defines class `Structure`.""" import codecs import copy as copymod @@ -87,7 +86,9 @@ class Structure(list): pdffit = None """None: default values for `pdffit`.""" - def __init__(self, atoms=None, lattice=None, title=None, filename=None, format=None): + def __init__( + self, atoms=None, lattice=None, title=None, filename=None, format=None + ): # if filename is specified load it and return if filename is not None: if any((atoms, lattice, title)): @@ -498,7 +499,9 @@ def __getitem__(self, idx): pass # check if there is any string label that should be resolved scalarstringlabel = isinstance(idx, str) - hasstringlabel = scalarstringlabel or (isiterable(idx) and any(isinstance(ii, str) for ii in idx)) + hasstringlabel = scalarstringlabel or ( + isiterable(idx) and any(isinstance(ii, str) for ii in idx) + ) # if not, use numpy indexing to resolve idx if not hasstringlabel: idx1 = idx @@ -694,7 +697,11 @@ def _set_lattice(self, value): self._lattice = value return - lattice = property(_get_lattice, _set_lattice, doc="Coordinate system for this `Structure`.") + lattice = property( + _get_lattice, + _set_lattice, + doc="Coordinate system for this `Structure`.", + ) # composition @@ -704,7 +711,10 @@ def _get_composition(self): rv[a.element] = rv.get(a.element, 0.0) + a.occupancy return rv - composition = property(_get_composition, doc="Dictionary of chemical symbols and their total occupancies.") + composition = property( + _get_composition, + doc="Dictionary of chemical symbols and their total occupancies.", + ) # linked atom attributes diff --git a/src/diffpy/structure/structureerrors.py b/src/diffpy/structure/structureerrors.py index c930b9b..8967936 100644 --- a/src/diffpy/structure/structureerrors.py +++ b/src/diffpy/structure/structureerrors.py @@ -13,8 +13,7 @@ # ############################################################################## -"""Exceptions used in Structure package. -""" +"""Exceptions used in Structure package.""" class StructureFormatError(Exception): diff --git a/src/diffpy/structure/symmetryutilities.py b/src/diffpy/structure/symmetryutilities.py index b58e7c8..06c7232 100644 --- a/src/diffpy/structure/symmetryutilities.py +++ b/src/diffpy/structure/symmetryutilities.py @@ -82,7 +82,9 @@ def check_tetragonal(): return a == b and alpha == beta == gamma == 90 def check_trigonal(): - rv = (a == b == c and alpha == beta == gamma) or (a == b and alpha == beta == 90 and gamma == 120) + rv = (a == b == c and alpha == beta == gamma) or ( + a == b and alpha == beta == 90 and gamma == 120 + ) return rv def check_hexagonal(): @@ -108,7 +110,9 @@ def check_cubic(): # isconstantFormula runs faster when regular expression is not # compiled per every single call. -_rx_constant_formula = re.compile(r"[-+]?(\d+(\.\d*)?|\.\d+)([eE][-+]?\d+)??(/[-+]?\d+)?$") +_rx_constant_formula = re.compile( + r"[-+]?(\d+(\.\d*)?|\.\d+)([eE][-+]?\d+)??(/[-+]?\d+)?$" +) def isconstantFormula(s): @@ -419,10 +423,27 @@ class GeneratorSite(object): ) """numpy.ndarray: 6x3x3 array of independent components of U matrices.""" - idx2Usymbol = {0: "U11", 1: "U12", 2: "U13", 3: "U12", 4: "U22", 5: "U23", 6: "U13", 7: "U23", 8: "U33"} + idx2Usymbol = { + 0: "U11", + 1: "U12", + 2: "U13", + 3: "U12", + 4: "U22", + 5: "U23", + 6: "U13", + 7: "U23", + 8: "U33", + } """dict: Mapping of index to standard U symbol.""" - def __init__(self, spacegroup, xyz, Uij=numpy.zeros((3, 3)), sgoffset=[0, 0, 0], eps=None): + def __init__( + self, + spacegroup, + xyz, + Uij=numpy.zeros((3, 3)), + sgoffset=[0, 0, 0], + eps=None, + ): if eps is None: eps = epsilon # just declare the members @@ -445,14 +466,18 @@ def __init__(self, spacegroup, xyz, Uij=numpy.zeros((3, 3)), sgoffset=[0, 0, 0], invariants = _findInvariants(ops) # shift self.xyz exactly to the special position if mult > 1: - xyzdups = numpy.array([op(xyz + self.sgoffset) - self.sgoffset for op in invariants]) + xyzdups = numpy.array( + [op(xyz + self.sgoffset) - self.sgoffset for op in invariants] + ) dxyz = xyzdups - xyz dxyz = numpy.mean(dxyz - dxyz.round(), axis=0) # recalculate if needed if numpy.any(dxyz != 0.0): self.xyz = xyz + dxyz self.xyz[numpy.fabs(self.xyz) < self.eps] = 0.0 - sites, ops, mult = expandPosition(spacegroup, self.xyz, self.sgoffset, eps) + sites, ops, mult = expandPosition( + spacegroup, self.xyz, self.sgoffset, eps + ) invariants = _findInvariants(ops) # self.xyz, sites, ops are all adjusted here self.eqxyz = sites @@ -547,7 +572,14 @@ def _findUSpace(self): n = len(self.invariants) R6zall = numpy.tile(-numpy.identity(6, dtype=float), (n, 1)) R6zall_iter = numpy.split(R6zall, n, axis=0) - i6kl = ((0, (0, 0)), (1, (1, 1)), (2, (2, 2)), (3, (0, 1)), (4, (0, 2)), (5, (1, 2))) + i6kl = ( + (0, (0, 0)), + (1, (1, 1)), + (2, (2, 2)), + (3, (0, 1)), + (4, (0, 2)), + (5, (1, 2)), + ) for op, R6z in zip(self.invariants, R6zall_iter): R = op.R for j, Ucj in enumerate(self.Ucomponents): @@ -575,7 +607,9 @@ def _findUParameters(self): for Usp in self.Uspace: Uspflat = Usp.flatten() Uspnorm2 = numpy.dot(Uspflat, Uspflat) - permidx = next(i for i, x in enumerate(Uspflat[diagorder]) if x == 1) + permidx = next( + i for i, x in enumerate(Uspflat[diagorder]) if x == 1 + ) idx = diagorder[permidx] vname = self.idx2Usymbol[idx] varvalue = numpy.dot(Uijflat, Uspflat) / Uspnorm2 @@ -635,14 +669,19 @@ def positionFormula(self, pos, xyzsymbols=("x", "y", "z")): for i in range(3): if abs(nvec[i]) < epsilon: continue - xyzformula[i] += "%s*%s " % (self.signedRatStr(nvec[i]), name2sym[vname]) + xyzformula[i] += "%s*%s " % ( + self.signedRatStr(nvec[i]), + name2sym[vname], + ) # add constant offset teqpos to all formulas for i in range(3): if xyzformula[i] and abs(teqpos[i]) < epsilon: continue xyzformula[i] += self.signedRatStr(teqpos[i]) # reduce unnecessary +1* and -1* - xyzformula = [re.sub("^[+]1[*]|(?<=[+-])1[*]", "", f).strip() for f in xyzformula] + xyzformula = [ + re.sub("^[+]1[*]|(?<=[+-])1[*]", "", f).strip() for f in xyzformula + ] return dict(zip(("x", "y", "z"), xyzformula)) def UFormula(self, pos, Usymbols=stdUsymbols): @@ -753,7 +792,9 @@ class ExpandAsymmetricUnit(object): # By design Atom instances are not accepted as arguments to keep # number of required imports low. - def __init__(self, spacegroup, corepos, coreUijs=None, sgoffset=[0, 0, 0], eps=None): + def __init__( + self, spacegroup, corepos, coreUijs=None, sgoffset=[0, 0, 0], eps=None + ): if eps is None: eps = epsilon # declare data members @@ -773,7 +814,9 @@ def __init__(self, spacegroup, corepos, coreUijs=None, sgoffset=[0, 0, 0], eps=N else: self.coreUijs = numpy.zeros((corelen, 3, 3), dtype=float) for cpos, cUij in zip(self.corepos, self.coreUijs): - gen = GeneratorSite(self.spacegroup, cpos, cUij, self.sgoffset, self.eps) + gen = GeneratorSite( + self.spacegroup, cpos, cUij, self.sgoffset, self.eps + ) self.multiplicity.append(gen.multiplicity) self.Uisotropy.append(gen.Uisotropy) self.expandedpos.append(gen.eqxyz) @@ -861,7 +904,9 @@ class SymmetryConstraints(object): List of bool flags for isotropic thermal displacements. """ - def __init__(self, spacegroup, positions, Uijs=None, sgoffset=[0, 0, 0], eps=None): + def __init__( + self, spacegroup, positions, Uijs=None, sgoffset=[0, 0, 0], eps=None + ): if eps is None: eps = epsilon # fill in data members @@ -906,7 +951,9 @@ def _findConstraints(self): numpos = len(self.positions) # canonical xyzsymbols and Usymbols xyzsymbols = [smbl + str(i) for i in range(numpos) for smbl in "xyz"] - Usymbols = [smbl + str(i) for i in range(numpos) for smbl in stdUsymbols] + Usymbols = [ + smbl + str(i) for i in range(numpos) for smbl in stdUsymbols + ] independent = set(range(numpos)) for genidx in range(numpos): if genidx not in independent: @@ -915,7 +962,9 @@ def _findConstraints(self): self.coremap[genidx] = [] genpos = self.positions[genidx] genUij = self.Uijs[genidx] - gen = GeneratorSite(self.spacegroup, genpos, genUij, self.sgoffset, self.eps) + gen = GeneratorSite( + self.spacegroup, genpos, genUij, self.sgoffset, self.eps + ) # append new pparameters if there are any gxyzsymbols = xyzsymbols[3 * genidx : 3 * (genidx + 1)] for k, v in gen.pparameters: @@ -976,7 +1025,9 @@ def positionFormulas(self, xyzsymbols=None): return list(self.poseqns) # check xyzsymbols if len(xyzsymbols) < len(self.pospars): - emsg = "Not enough symbols for %i position parameters" % len(self.pospars) + emsg = "Not enough symbols for %i position parameters" % len( + self.pospars + ) raise SymmetryError(emsg) # build translation dictionary trsmbl = dict(zip(self.posparSymbols(), xyzsymbols)) @@ -1010,7 +1061,10 @@ def positionFormulasPruned(self, xyzsymbols=None): list List of coordinate formula dictionaries. """ - rv = [pruneFormulaDictionary(eqns) for eqns in self.positionFormulas(xyzsymbols)] + rv = [ + pruneFormulaDictionary(eqns) + for eqns in self.positionFormulas(xyzsymbols) + ] return rv def UparSymbols(self): @@ -1077,7 +1131,9 @@ def UFormulasPruned(self, Usymbols=None): List of atom displacement formulas in tuples of ``(U11, U22, U33, U12, U13, U23)``. """ - rv = [pruneFormulaDictionary(eqns) for eqns in self.UFormulas(Usymbols)] + rv = [ + pruneFormulaDictionary(eqns) for eqns in self.UFormulas(Usymbols) + ] return rv diff --git a/src/diffpy/structure/utils.py b/src/diffpy/structure/utils.py index e5fa3ce..4fcee68 100644 --- a/src/diffpy/structure/utils.py +++ b/src/diffpy/structure/utils.py @@ -13,8 +13,7 @@ # ############################################################################## -"""Small shared functions. -""" +"""Small shared functions.""" from collections.abc import Iterable as _Iterable diff --git a/tests/test_lattice.py b/tests/test_lattice.py index a2b22d3..e3549ab 100644 --- a/tests/test_lattice.py +++ b/tests/test_lattice.py @@ -13,8 +13,7 @@ # ############################################################################## -"""Unit tests for Lattice class. -""" +"""Unit tests for Lattice class.""" import unittest @@ -37,7 +36,12 @@ def setUp(self): def test___init__(self): """Check Lattice.__init__ processing of arguments.""" self.assertRaises(ValueError, Lattice, self.lattice, c=4) - self.assertRaises(ValueError, Lattice, base=self.lattice.base, baserot=self.lattice.baserot) + self.assertRaises( + ValueError, + Lattice, + base=self.lattice.base, + baserot=self.lattice.baserot, + ) self.assertRaises(ValueError, Lattice, 1, 2, 3) self.assertRaises(ValueError, Lattice, 1, 2, 3, 80, 90) L0 = self.lattice @@ -69,9 +73,15 @@ def cosd(x): self.assertAlmostEqual(1.0, norm(base[0]), self.places) self.assertAlmostEqual(2.0, norm(base[1]), self.places) self.assertAlmostEqual(3.0, norm(base[2]), self.places) - self.assertAlmostEqual(cosd(80.0), dot(base[1], base[2]) / (2 * 3), self.places) - self.assertAlmostEqual(cosd(100.0), dot(base[0], base[2]) / (1 * 3), self.places) - self.assertAlmostEqual(cosd(120.0), dot(base[0], base[1]) / (1 * 2), self.places) + self.assertAlmostEqual( + cosd(80.0), dot(base[1], base[2]) / (2 * 3), self.places + ) + self.assertAlmostEqual( + cosd(100.0), dot(base[0], base[2]) / (1 * 3), self.places + ) + self.assertAlmostEqual( + cosd(120.0), dot(base[0], base[1]) / (1 * 2), self.places + ) return def test_latpar_properties(self): @@ -156,8 +166,16 @@ def test_setLatBase(self): self.assertTrue(numpy.allclose(base[1], self.lattice.base[1])) self.assertTrue(numpy.allclose(base[2], self.lattice.base[2])) # try base checking - self.assertRaises(LatticeError, self.lattice.setLatBase, [[1, 0, 0], [1, 0, 0], [0, 0, 1]]) - self.assertRaises(LatticeError, self.lattice.setLatBase, [[1, 0, 0], [0, 0, 1], [0, 1, 0]]) + self.assertRaises( + LatticeError, + self.lattice.setLatBase, + [[1, 0, 0], [1, 0, 0], [0, 0, 1]], + ) + self.assertRaises( + LatticeError, + self.lattice.setLatBase, + [[1, 0, 0], [0, 0, 1], [0, 1, 0]], + ) return def test_reciprocal(self): @@ -229,7 +247,9 @@ def test_angle(self): v = [0.3, 0.7, 0.7] uc = L.cartesian(u) vc = L.cartesian(v) - a0 = degrees(acos(numpy.dot(uc, vc) / (numalg.norm(uc) * numalg.norm(vc)))) + a0 = degrees( + acos(numpy.dot(uc, vc) / (numalg.norm(uc) * numalg.norm(vc))) + ) self.assertAlmostEqual(a0, L.angle(u, v), self.places) self.assertAlmostEqual(a0, L.angle(v, u), self.places) u5 = numpy.tile(u, (5, 1)) diff --git a/tests/test_loadstructure.py b/tests/test_loadstructure.py index 4f099c7..ad19742 100644 --- a/tests/test_loadstructure.py +++ b/tests/test_loadstructure.py @@ -1,7 +1,6 @@ #!/usr/bin/env python -"""Unit tests for the loadStructure factory. -""" +"""Unit tests for the loadStructure factory.""" import unittest diff --git a/tests/test_p_cif.py b/tests/test_p_cif.py index 62bb25d..b38eb49 100644 --- a/tests/test_p_cif.py +++ b/tests/test_p_cif.py @@ -13,8 +13,7 @@ # ############################################################################## -"""Unit tests for diffpy.structure.parsers.p_cif module -""" +"""Unit tests for diffpy.structure.parsers.p_cif module""" import unittest @@ -95,7 +94,9 @@ def test_parse(self): stru = ptest.parse(sgood) self.assertEqual(str(stru_check), str(stru)) self.assertEqual(str(stru_check.lattice), str(stru.lattice)) - self.assertEqual(pfile.spacegroup.short_name, ptest.spacegroup.short_name) + self.assertEqual( + pfile.spacegroup.short_name, ptest.spacegroup.short_name + ) ptestb = P_cif() self.assertRaises(StructureFormatError, ptestb.parse, sbad) return @@ -111,7 +112,9 @@ def test_parseLines(self): stru = ptest.parseLines(goodlines) self.assertEqual(str(stru_check), str(stru)) self.assertEqual(str(stru_check.lattice), str(stru.lattice)) - self.assertEqual(pfile.spacegroup.short_name, ptest.spacegroup.short_name) + self.assertEqual( + pfile.spacegroup.short_name, ptest.spacegroup.short_name + ) ptest2 = P_cif() self.assertRaises(StructureFormatError, ptest2.parseLines, badlines) return @@ -137,7 +140,9 @@ def test_parseFile(self): self.assertEqual(0.0225566, a0.Uisoequiv) # badciffile pfile2 = P_cif() - self.assertRaises(StructureFormatError, pfile2.parseFile, self.badciffile) + self.assertRaises( + StructureFormatError, pfile2.parseFile, self.badciffile + ) # graphite pgraphite = P_cif() graphite = pgraphite.parseFile(self.graphiteciffile) @@ -298,7 +303,11 @@ def test_spacegroup_isotropy(self): "verify site isotropy due to site symmetry." # remove the _atom_site_thermal_displace_type field with open(self.pbteciffile) as fp: - lines = [line.replace(" Uiso ", " ") for line in fp if "_atom_site_thermal_displace_type" not in line] + lines = [ + line.replace(" Uiso ", " ") + for line in fp + if "_atom_site_thermal_displace_type" not in line + ] ciftxt = "".join(lines) ptest = self.ptest stru = ptest.parse(ciftxt) @@ -345,7 +354,11 @@ def test_adp_type_iso(self): def test_adp_aniso_label(self): "verify ADP type setting from _atom_site_aniso_label loop" with open(self.teiciffile) as fp: - lines = [line.replace(" Uani ", " ") for line in fp if "_atom_site_adp_type" not in line] + lines = [ + line.replace(" Uani ", " ") + for line in fp + if "_atom_site_adp_type" not in line + ] ciftxt = "".join(lines) stru = self.ptest.parse(ciftxt) self.assertTrue(all(stru.anisotropy)) diff --git a/tests/test_p_discus.py b/tests/test_p_discus.py index 8959718..4aa9c48 100644 --- a/tests/test_p_discus.py +++ b/tests/test_p_discus.py @@ -13,8 +13,7 @@ # ############################################################################## -"""Unit tests for diffpy.structure.parsers.p_discus module -""" +"""Unit tests for diffpy.structure.parsers.p_discus module""" import re import unittest @@ -81,7 +80,9 @@ def test_except_other_formats(self): ] for ft in badfiles: ff = self.datafile(ft) - self.assertRaises(StructureFormatError, self.stru.read, ff, format=self.format) + self.assertRaises( + StructureFormatError, self.stru.read, ff, format=self.format + ) return def test_ignored_lines(self): @@ -97,7 +98,9 @@ def test_ignored_lines(self): self.assertEqual([r1.rstrip(), r2.rstrip()], p.ignored_lines) ni_lines.append(r1) s_s2 = "".join(ni_lines) - self.assertRaises(StructureFormatError, self.stru.readStr, s_s2, self.format) + self.assertRaises( + StructureFormatError, self.stru.readStr, s_s2, self.format + ) return def test_spdiameter_parsing(self): @@ -118,7 +121,9 @@ def test_spdiameter_parsing(self): ni_lines = fp.readlines() ni_lines.insert(3, "shape invalid, 7\n") sbad = "".join(ni_lines) - self.assertRaises(StructureFormatError, self.stru.readStr, sbad, format=self.format) + self.assertRaises( + StructureFormatError, self.stru.readStr, sbad, format=self.format + ) return def test_stepcut_parsing(self): @@ -139,7 +144,9 @@ def test_stepcut_parsing(self): ni_lines = fp.readlines() ni_lines.insert(3, "shape invalid, 7\n") sbad = "".join(ni_lines) - self.assertRaises(StructureFormatError, self.stru.readStr, sbad, format=self.format) + self.assertRaises( + StructureFormatError, self.stru.readStr, sbad, format=self.format + ) return diff --git a/tests/test_p_pdffit.py b/tests/test_p_pdffit.py index f993cb4..a521de3 100644 --- a/tests/test_p_pdffit.py +++ b/tests/test_p_pdffit.py @@ -13,8 +13,7 @@ # ############################################################################## -"""Unit tests for diffpy.structure.parsers.p_pdffit module -""" +"""Unit tests for diffpy.structure.parsers.p_pdffit module""" import re import unittest @@ -143,7 +142,10 @@ def test_read_pdffit_Ni_prim123(self): s_o = a5.occupancy f_o = 1.0 self.assertAlmostEqual(s_o, f_o) - s_U = [a5.U[ij[0], ij[1]] for ij in [(0, 0), (1, 1), (2, 2), (0, 1), (0, 2), (1, 2)]] + s_U = [ + a5.U[ij[0], ij[1]] + for ij in [(0, 0), (1, 1), (2, 2), (0, 1), (0, 2), (1, 2)] + ] f_U = 3 * [0.00126651] + 3 * [-0.00042217] for i in range(len(s_U)): self.assertAlmostEqual(s_U[i], f_U[i]) @@ -152,8 +154,18 @@ def test_read_pdffit_Ni_prim123(self): def test_read_pdffit_bad(self): """check exceptions when reading invalid pdffit file""" stru = self.stru - self.assertRaises(StructureFormatError, stru.read, self.datafile("Ni-bad.stru"), self.format) - self.assertRaises(StructureFormatError, stru.read, self.datafile("bucky.xyz"), self.format) + self.assertRaises( + StructureFormatError, + stru.read, + self.datafile("Ni-bad.stru"), + self.format, + ) + self.assertRaises( + StructureFormatError, + stru.read, + self.datafile("bucky.xyz"), + self.format, + ) return def test_writeStr_pdffit(self): @@ -192,7 +204,9 @@ def test_ignored_lines(self): self.assertEqual([r1, r2], p.ignored_lines) ni_lines.insert(-3, r1 + "\n") s_s2 = "".join(ni_lines) - self.assertRaises(StructureFormatError, self.stru.readStr, s_s2, self.format) + self.assertRaises( + StructureFormatError, self.stru.readStr, s_s2, self.format + ) return def test_spdiameter_parsing(self): @@ -213,7 +227,9 @@ def test_spdiameter_parsing(self): ni_lines = fp.readlines() ni_lines.insert(3, "shape invalid, 7\n") sbad = "".join(ni_lines) - self.assertRaises(StructureFormatError, self.stru.readStr, sbad, format=self.format) + self.assertRaises( + StructureFormatError, self.stru.readStr, sbad, format=self.format + ) return def test_stepcut_parsing(self): @@ -234,7 +250,9 @@ def test_stepcut_parsing(self): ni_lines = fp.readlines() ni_lines.insert(3, "shape invalid, 7\n") sbad = "".join(ni_lines) - self.assertRaises(StructureFormatError, self.stru.readStr, sbad, format=self.format) + self.assertRaises( + StructureFormatError, self.stru.readStr, sbad, format=self.format + ) return diff --git a/tests/test_parsers.py b/tests/test_parsers.py index a3f7f3c..bd88658 100644 --- a/tests/test_parsers.py +++ b/tests/test_parsers.py @@ -13,8 +13,7 @@ # ############################################################################## -"""Unit tests for structure.parsers module. -""" +"""Unit tests for structure.parsers module.""" import os import re @@ -65,10 +64,30 @@ def test_read_xyz(self): def test_read_xyz_bad(self): """check exceptions when reading invalid xyz file""" stru = self.stru - self.assertRaises(StructureFormatError, stru.read, self.datafile("bucky-bad1.xyz"), self.format) - self.assertRaises(StructureFormatError, stru.read, self.datafile("bucky-bad2.xyz"), self.format) - self.assertRaises(StructureFormatError, stru.read, self.datafile("bucky-plain.xyz"), self.format) - self.assertRaises(StructureFormatError, stru.read, self.datafile("hexagon-raw.xy"), self.format) + self.assertRaises( + StructureFormatError, + stru.read, + self.datafile("bucky-bad1.xyz"), + self.format, + ) + self.assertRaises( + StructureFormatError, + stru.read, + self.datafile("bucky-bad2.xyz"), + self.format, + ) + self.assertRaises( + StructureFormatError, + stru.read, + self.datafile("bucky-plain.xyz"), + self.format, + ) + self.assertRaises( + StructureFormatError, + stru.read, + self.datafile("hexagon-raw.xy"), + self.format, + ) return def test_writeStr_xyz(self): @@ -128,7 +147,12 @@ def test_read_plainxyz(self): def test_read_plainxyz_bad(self): """check exceptions when reading invalid plain xyz file""" stru = self.stru - self.assertRaises(StructureFormatError, stru.read, self.datafile("bucky-plain-bad.xyz"), self.format) + self.assertRaises( + StructureFormatError, + stru.read, + self.datafile("bucky-plain-bad.xyz"), + self.format, + ) return def test_read_rawxyz(self): @@ -146,8 +170,18 @@ def test_read_rawxyz(self): def test_read_rawxyz_bad(self): """check exceptions when reading unsupported xy file""" stru = self.stru - self.assertRaises(StructureFormatError, stru.read, self.datafile("hexagon-raw-bad.xyz"), self.format) - self.assertRaises(StructureFormatError, stru.read, self.datafile("hexagon-raw.xy"), self.format) + self.assertRaises( + StructureFormatError, + stru.read, + self.datafile("hexagon-raw-bad.xyz"), + self.format, + ) + self.assertRaises( + StructureFormatError, + stru.read, + self.datafile("hexagon-raw.xy"), + self.format, + ) return def test_writeStr_rawxyz(self): diff --git a/tests/test_spacegroups.py b/tests/test_spacegroups.py index c9980e1..e6a8606 100644 --- a/tests/test_spacegroups.py +++ b/tests/test_spacegroups.py @@ -13,8 +13,7 @@ # ############################################################################## -"""Unit tests for diffpy.structure.spacegroups -""" +"""Unit tests for diffpy.structure.spacegroups""" import unittest @@ -83,7 +82,9 @@ def test_FindSpaceGroup(self): self.assertIsNot(sg123, sg123r) self.assertIsNot(sg123.symop_list, sg123r.symop_list) self.assertEqual(ops123[::-1], sg123r.symop_list) - self.assertEqual(_hashSymOpList(sg123.symop_list), _hashSymOpList(sg123r.symop_list)) + self.assertEqual( + _hashSymOpList(sg123.symop_list), _hashSymOpList(sg123r.symop_list) + ) self.assertIs(sg123, FindSpaceGroup(ops123[::-1], shuffle=True)) return @@ -96,27 +97,38 @@ def test__hashSymOpList(self): def test_spacegroup_representation(self): """Verify SpaceGroup.__repr__().""" self.assertEqual( - repr(GetSpaceGroup(1)), "SpaceGroup #1 (P1, Triclinic). Symmetry matrices: 1, point sym. matr.: 1" + repr(GetSpaceGroup(1)), + "SpaceGroup #1 (P1, Triclinic). Symmetry matrices: 1, point sym. matr.: 1", ) self.assertEqual( - repr(GetSpaceGroup(3)), "SpaceGroup #3 (P2, Monoclinic). Symmetry matrices: 2, point sym. matr.: 2" + repr(GetSpaceGroup(3)), + "SpaceGroup #3 (P2, Monoclinic). Symmetry matrices: 2, point sym. matr.: 2", ) self.assertEqual( repr(GetSpaceGroup(16)), - ("SpaceGroup #16 (P222, Orthorhombic). Symmetry matrices: 4, point sym. " "matr.: 4"), + ( + "SpaceGroup #16 (P222, Orthorhombic). Symmetry matrices: 4, point sym. " + "matr.: 4" + ), ) self.assertEqual( - repr(GetSpaceGroup(75)), "SpaceGroup #75 (P4, Tetragonal). Symmetry matrices: 4, point sym. matr.: 4" + repr(GetSpaceGroup(75)), + "SpaceGroup #75 (P4, Tetragonal). Symmetry matrices: 4, point sym. matr.: 4", ) self.assertEqual( - repr(GetSpaceGroup(143)), "SpaceGroup #143 (P3, Trigonal). Symmetry matrices: 3, point sym. matr.: 3" + repr(GetSpaceGroup(143)), + "SpaceGroup #143 (P3, Trigonal). Symmetry matrices: 3, point sym. matr.: 3", ) self.assertEqual( - repr(GetSpaceGroup(168)), "SpaceGroup #168 (P6, Hexagonal). Symmetry matrices: 6, point sym. matr.: 6" + repr(GetSpaceGroup(168)), + "SpaceGroup #168 (P6, Hexagonal). Symmetry matrices: 6, point sym. matr.: 6", ) self.assertEqual( repr(GetSpaceGroup(229)), - ("SpaceGroup #229 (Im-3m, Cubic). Symmetry matrices: 96, point sym. " "matr.: 48"), + ( + "SpaceGroup #229 (Im-3m, Cubic). Symmetry matrices: 96, point sym. " + "matr.: 48" + ), ) return diff --git a/tests/test_structure.py b/tests/test_structure.py index 9c1a630..30eaab8 100644 --- a/tests/test_structure.py +++ b/tests/test_structure.py @@ -13,8 +13,7 @@ # ############################################################################## -"""Unit tests for Structure class. -""" +"""Unit tests for Structure class.""" import copy @@ -41,7 +40,10 @@ def prepare_fixture(self, datafile): _loaded_structures = {} def setUp(self): - self.stru = Structure([Atom("C", [0, 0, 0]), Atom("C", [1, 1, 1])], lattice=Lattice(1, 1, 1, 90, 90, 120)) + self.stru = Structure( + [Atom("C", [0, 0, 0]), Atom("C", [1, 1, 1])], + lattice=Lattice(1, 1, 1, 90, 90, 120), + ) # useful variables if not self._loaded_structures: @@ -60,8 +62,12 @@ def test___init__(self): """check Structure.__init__()""" atoms = [Atom("C", [0, 0, 0]), Atom("C", [0.5, 0.5, 0.5])] self.assertRaises(ValueError, Structure, atoms, filename=self.teifile) - self.assertRaises(ValueError, Structure, lattice=Lattice(), filename=self.teifile) - self.assertRaises(ValueError, Structure, title="test", filename=self.teifile) + self.assertRaises( + ValueError, Structure, lattice=Lattice(), filename=self.teifile + ) + self.assertRaises( + ValueError, Structure, title="test", filename=self.teifile + ) stru1 = Structure(title="my title") self.assertEqual("my title", stru1.title) stru2a = Structure(atoms) @@ -134,8 +140,12 @@ def test_distance(self): self.stru.assignUniqueLabels() self.assertRaises(IndexError, self.stru.distance, 333, "C1") self.assertRaises(IndexError, self.stru.distance, "C", "C1") - self.assertAlmostEqual(sqrt(2.0), self.stru.distance(0, 1), self.places) - self.assertAlmostEqual(sqrt(2.0), self.stru.distance("C1", "C2"), self.places) + self.assertAlmostEqual( + sqrt(2.0), self.stru.distance(0, 1), self.places + ) + self.assertAlmostEqual( + sqrt(2.0), self.stru.distance("C1", "C2"), self.places + ) self.assertEqual(0, self.stru.distance(0, "C1")) return @@ -239,7 +249,9 @@ def test___getitem__(self): cdse[0].label = "Hohenzollern" self.assertRaises(IndexError, cdse.__getitem__, "Cd1") self.assertTrue(cdse[0] is cdse["Hohenzollern"]) - self.assertEqual([cdse[0], cdse[3], cdse[1]], cdse["Hohenzollern", 3:0:-2].tolist()) + self.assertEqual( + [cdse[0], cdse[3], cdse[1]], cdse["Hohenzollern", 3:0:-2].tolist() + ) stru.label = ["A", "B"] self.assertTrue(stru[0] is stru["A"]) self.assertTrue(stru[1] is stru["B"]) @@ -349,8 +361,14 @@ def test___mul__(self): self.assertEqual(12, len(set(cdse * 3))) cdsex3 = 3 * cdse self.assertEqual(12, len(cdsex3)) - self.assertEqual(3 * "Cd Cd Se Se".split(), [a.element for a in cdsex3]) - self.assertTrue(numpy.array_equal(3 * [a.xyz for a in cdse], [a.xyz for a in cdsex3])) + self.assertEqual( + 3 * "Cd Cd Se Se".split(), [a.element for a in cdsex3] + ) + self.assertTrue( + numpy.array_equal( + 3 * [a.xyz for a in cdse], [a.xyz for a in cdsex3] + ) + ) self.assertFalse(set(cdse).intersection(cdsex3)) self.assertFalse(cdse.lattice is cdsex3.lattice) return @@ -484,7 +502,9 @@ def test_xyz_cartn(self): """check Structure.xyz_cartn""" pbte = copy.copy(self.pbte) self.assertEqual((8, 3), pbte.xyz_cartn.shape) - self.assertTrue(numpy.allclose(6.461 / 2.0 * numpy.ones(3), pbte.xyz_cartn[0])) + self.assertTrue( + numpy.allclose(6.461 / 2.0 * numpy.ones(3), pbte.xyz_cartn[0]) + ) pbte.xyz_cartn += numpy.array([0.1, 0.2, 0.3]) * 6.461 self.assertTrue(numpy.allclose([0.6, 0.7, 0.8], pbte[0].xyz)) self.assertTrue(numpy.allclose([0.6, 0.7, 0.3], pbte[7].xyz)) @@ -502,7 +522,9 @@ def test_anisotropy(self): self.assertAlmostEqual(0.019227, tei[0].U22, 6) self.assertAlmostEqual(0.019227, tei[0].U33, 6) self.assertAlmostEqual(0.0, tei[0].U12, 6) - self.assertAlmostEqual(0.019227 * -numpy.cos(numpy.radians(128.09)), tei[0].U13, 6) + self.assertAlmostEqual( + 0.019227 * -numpy.cos(numpy.radians(128.09)), tei[0].U13, 6 + ) self.assertAlmostEqual(0.0, tei[0].U23, 6) self.assertAlmostEqual(0.019227, tei[0].Uisoequiv, 6) return diff --git a/tests/test_supercell.py b/tests/test_supercell.py index 0e840df..68aa809 100644 --- a/tests/test_supercell.py +++ b/tests/test_supercell.py @@ -13,8 +13,7 @@ # ############################################################################## -"""Unit tests for supercell.py -""" +"""Unit tests for supercell.py""" import unittest diff --git a/tests/test_symmetryutilities.py b/tests/test_symmetryutilities.py index c4de983..7b00c42 100644 --- a/tests/test_symmetryutilities.py +++ b/tests/test_symmetryutilities.py @@ -13,8 +13,7 @@ # ############################################################################## -"""Unit tests for SymmetryUtilities.py -""" +"""Unit tests for SymmetryUtilities.py""" import re import sys @@ -270,14 +269,70 @@ def test_UFormula(self): # Ref: Willis and Pryor, Thermal Vibrations in Crystallography, # Cambridge University Press 1975, p. 104-110 smbl = ("A", "B", "C", "D", "E", "F") - norule = {"U11": "A", "U22": "B", "U33": "C", "U12": "D", "U13": "E", "U23": "F"} - rule05 = {"U11": "A", "U22": "A", "U33": "C", "U12": "D", "U13": "0", "U23": "0"} - rule06 = {"U11": "A", "U22": "A", "U33": "C", "U12": "D", "U13": "E", "U23": "E"} - rule07 = {"U11": "A", "U22": "A", "U33": "C", "U12": "D", "U13": "E", "U23": "-E"} - rule15 = {"U11": "A", "U22": "B", "U33": "C", "U12": "0.5*B", "U13": "0.5*F", "U23": "F"} - rule16 = {"U11": "A", "U22": "A", "U33": "C", "U12": "0.5*A", "U13": "0", "U23": "0"} - rule17 = {"U11": "A", "U22": "A", "U33": "A", "U12": "0", "U13": "0", "U23": "0"} - rule18 = {"U11": "A", "U22": "A", "U33": "A", "U12": "D", "U13": "D", "U23": "D"} + norule = { + "U11": "A", + "U22": "B", + "U33": "C", + "U12": "D", + "U13": "E", + "U23": "F", + } + rule05 = { + "U11": "A", + "U22": "A", + "U33": "C", + "U12": "D", + "U13": "0", + "U23": "0", + } + rule06 = { + "U11": "A", + "U22": "A", + "U33": "C", + "U12": "D", + "U13": "E", + "U23": "E", + } + rule07 = { + "U11": "A", + "U22": "A", + "U33": "C", + "U12": "D", + "U13": "E", + "U23": "-E", + } + rule15 = { + "U11": "A", + "U22": "B", + "U33": "C", + "U12": "0.5*B", + "U13": "0.5*F", + "U23": "F", + } + rule16 = { + "U11": "A", + "U22": "A", + "U33": "C", + "U12": "0.5*A", + "U13": "0", + "U23": "0", + } + rule17 = { + "U11": "A", + "U22": "A", + "U33": "A", + "U12": "0", + "U13": "0", + "U23": "0", + } + rule18 = { + "U11": "A", + "U22": "A", + "U33": "A", + "U12": "D", + "U13": "D", + "U23": "D", + } ufm = self.g117c.UFormula(self.g117c.xyz, smbl) self.assertEqual(rule05, ufm) ufm = self.g117h.UFormula(self.g117h.xyz, smbl) @@ -319,12 +374,54 @@ def test_UFormula_g186c_eqxyz(self): """Check rotated U formulas at the symmetry positions of c-site in 186.""" sg186 = GetSpaceGroup(186) crules = [ - {"U11": "A", "U22": "A", "U33": "C", "U12": "D", "U13": "E", "U23": "-E"}, - {"U11": "A", "U22": "2*A-2*D", "U33": "C", "U12": "A-D", "U13": "E", "U23": "2*E"}, - {"U11": "2*A-2*D", "U22": "A", "U33": "C", "U12": "A-D", "U13": "-2*E", "U23": "-E"}, - {"U11": "A", "U22": "A", "U33": "C", "U12": "D", "U13": "-E", "U23": "E"}, - {"U11": "A", "U22": "2*A-2*D", "U33": "C", "U12": "A-D", "U13": "-E", "U23": "-2*E"}, - {"U11": "2*A-2*D", "U22": "A", "U33": "C", "U12": "A-D", "U13": "2*E", "U23": "E"}, + { + "U11": "A", + "U22": "A", + "U33": "C", + "U12": "D", + "U13": "E", + "U23": "-E", + }, + { + "U11": "A", + "U22": "2*A-2*D", + "U33": "C", + "U12": "A-D", + "U13": "E", + "U23": "2*E", + }, + { + "U11": "2*A-2*D", + "U22": "A", + "U33": "C", + "U12": "A-D", + "U13": "-2*E", + "U23": "-E", + }, + { + "U11": "A", + "U22": "A", + "U33": "C", + "U12": "D", + "U13": "-E", + "U23": "E", + }, + { + "U11": "A", + "U22": "2*A-2*D", + "U33": "C", + "U12": "A-D", + "U13": "-E", + "U23": "-2*E", + }, + { + "U11": "2*A-2*D", + "U22": "A", + "U33": "C", + "U12": "A-D", + "U13": "2*E", + "U23": "E", + }, ] self.assertEqual(6, len(self.g186c.eqxyz)) gc = self.g186c @@ -335,13 +432,22 @@ def test_UFormula_g186c_eqxyz(self): for u in eau.expandedUijs: du = numpy.linalg.norm((uiso - u).flatten()) self.assertAlmostEqual(0.0, du, 8) - symcon = SymmetryConstraints(sg186, sum(eau.expandedpos, []), sum(eau.expandedUijs, [])) + symcon = SymmetryConstraints( + sg186, sum(eau.expandedpos, []), sum(eau.expandedUijs, []) + ) upd = dict(symcon.Upars) self.assertEqual(2.0, upd["U110"]) self.assertEqual(2.0, upd["U330"]) self.assertEqual(1.0, upd["U120"]) self.assertEqual(0.0, upd["U130"]) - uisod = {"U11": 2.0, "U22": 2.0, "U33": 2.0, "U12": 1.0, "U13": 0.0, "U23": 0.0} + uisod = { + "U11": 2.0, + "U22": 2.0, + "U33": 2.0, + "U12": 1.0, + "U13": 0.0, + "U23": 0.0, + } for ufms in symcon.UFormulas(): for n, fm in ufms.items(): self.assertEqual(uisod[n], eval(fm, upd)) @@ -350,7 +456,11 @@ def test_UFormula_g186c_eqxyz(self): def test_UFormula_self_reference(self): "Ensure U formulas have no self reference such as U13=0.5*U13." for g in self.generators.values(): - badformulas = [(n, fm) for n, fm in g.UFormula(g.xyz).items() if n in fm and n != fm] + badformulas = [ + (n, fm) + for n, fm in g.UFormula(g.xyz).items() + if n in fm and n != fm + ] self.assertEqual([], badformulas) return diff --git a/tests/test_version.py b/tests/test_version.py index e62433e..de45655 100644 --- a/tests/test_version.py +++ b/tests/test_version.py @@ -1,5 +1,4 @@ -"""Unit tests for __version__.py -""" +"""Unit tests for __version__.py""" import diffpy.structure