structuretoolkit 0.0.42__tar.gz → 0.0.44__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- structuretoolkit-0.0.44/.gitignore +217 -0
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/PKG-INFO +9 -10
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/pyproject.toml +9 -10
- structuretoolkit-0.0.44/src/structuretoolkit/_version.py +24 -0
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/analyse/dscribe.py +1 -1
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/analyse/neighbors.py +48 -49
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/analyse/phonopy.py +2 -0
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/analyse/pyscal.py +2 -2
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/analyse/snap.py +7 -7
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/analyse/spatial.py +20 -17
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/analyse/strain.py +20 -10
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/analyse/symmetry.py +35 -19
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/build/__init__.py +5 -3
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/build/compound.py +2 -2
- structuretoolkit-0.0.44/src/structuretoolkit/build/geometry.py +138 -0
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/build/materialsproject.py +4 -2
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/build/mesh.py +10 -8
- structuretoolkit-0.0.44/src/structuretoolkit/build/sqs/__init__.py +33 -0
- structuretoolkit-0.0.44/src/structuretoolkit/build/sqs/_interface.py +322 -0
- structuretoolkit-0.0.44/src/structuretoolkit/build/sqs/_types.py +196 -0
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/common/helper.py +11 -11
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/common/pymatgen.py +1 -1
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/visualize.py +8 -3
- structuretoolkit-0.0.42/.gitignore +0 -10
- structuretoolkit-0.0.42/src/structuretoolkit/_version.py +0 -34
- structuretoolkit-0.0.42/src/structuretoolkit/build/sqs.py +0 -236
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/LICENSE +0 -0
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/README.md +0 -0
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/__init__.py +0 -0
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/analyse/__init__.py +0 -0
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/analyse/distance.py +0 -0
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/build/aimsgb.py +0 -0
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/build/surface.py +0 -0
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/common/__init__.py +0 -0
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/common/error.py +0 -0
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/common/phonopy.py +0 -0
- {structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/common/pyscal.py +0 -0
|
@@ -0,0 +1,217 @@
|
|
|
1
|
+
# Byte-compiled / optimized / DLL files
|
|
2
|
+
__pycache__/
|
|
3
|
+
*.py[codz]
|
|
4
|
+
*$py.class
|
|
5
|
+
|
|
6
|
+
# C extensions
|
|
7
|
+
*.so
|
|
8
|
+
|
|
9
|
+
# Distribution / packaging
|
|
10
|
+
.Python
|
|
11
|
+
develop-eggs/
|
|
12
|
+
dist/
|
|
13
|
+
downloads/
|
|
14
|
+
eggs/
|
|
15
|
+
.eggs/
|
|
16
|
+
lib/
|
|
17
|
+
lib64/
|
|
18
|
+
parts/
|
|
19
|
+
sdist/
|
|
20
|
+
var/
|
|
21
|
+
wheels/
|
|
22
|
+
share/python-wheels/
|
|
23
|
+
*.egg-info/
|
|
24
|
+
.installed.cfg
|
|
25
|
+
*.egg
|
|
26
|
+
MANIFEST
|
|
27
|
+
|
|
28
|
+
# PyInstaller
|
|
29
|
+
# Usually these files are written by a python script from a template
|
|
30
|
+
# before PyInstaller builds the exe, so as to inject date/other infos into it.
|
|
31
|
+
*.manifest
|
|
32
|
+
*.spec
|
|
33
|
+
|
|
34
|
+
# Installer logs
|
|
35
|
+
pip-log.txt
|
|
36
|
+
pip-delete-this-directory.txt
|
|
37
|
+
|
|
38
|
+
# Unit test / coverage reports
|
|
39
|
+
htmlcov/
|
|
40
|
+
.tox/
|
|
41
|
+
.nox/
|
|
42
|
+
.coverage
|
|
43
|
+
.coverage.*
|
|
44
|
+
.cache
|
|
45
|
+
nosetests.xml
|
|
46
|
+
coverage.xml
|
|
47
|
+
*.cover
|
|
48
|
+
*.py.cover
|
|
49
|
+
.hypothesis/
|
|
50
|
+
.pytest_cache/
|
|
51
|
+
cover/
|
|
52
|
+
|
|
53
|
+
# Translations
|
|
54
|
+
*.mo
|
|
55
|
+
*.pot
|
|
56
|
+
|
|
57
|
+
# Django stuff:
|
|
58
|
+
*.log
|
|
59
|
+
local_settings.py
|
|
60
|
+
db.sqlite3
|
|
61
|
+
db.sqlite3-journal
|
|
62
|
+
|
|
63
|
+
# Flask stuff:
|
|
64
|
+
instance/
|
|
65
|
+
.webassets-cache
|
|
66
|
+
|
|
67
|
+
# Scrapy stuff:
|
|
68
|
+
.scrapy
|
|
69
|
+
|
|
70
|
+
# Sphinx documentation
|
|
71
|
+
docs/_build/
|
|
72
|
+
|
|
73
|
+
# PyBuilder
|
|
74
|
+
.pybuilder/
|
|
75
|
+
target/
|
|
76
|
+
|
|
77
|
+
# Jupyter Notebook
|
|
78
|
+
.ipynb_checkpoints
|
|
79
|
+
|
|
80
|
+
# IPython
|
|
81
|
+
profile_default/
|
|
82
|
+
ipython_config.py
|
|
83
|
+
|
|
84
|
+
# pyenv
|
|
85
|
+
# For a library or package, you might want to ignore these files since the code is
|
|
86
|
+
# intended to run in multiple environments; otherwise, check them in:
|
|
87
|
+
# .python-version
|
|
88
|
+
|
|
89
|
+
# pipenv
|
|
90
|
+
# According to pypa/pipenv#598, it is recommended to include Pipfile.lock in version control.
|
|
91
|
+
# However, in case of collaboration, if having platform-specific dependencies or dependencies
|
|
92
|
+
# having no cross-platform support, pipenv may install dependencies that don't work, or not
|
|
93
|
+
# install all needed dependencies.
|
|
94
|
+
# Pipfile.lock
|
|
95
|
+
|
|
96
|
+
# UV
|
|
97
|
+
# Similar to Pipfile.lock, it is generally recommended to include uv.lock in version control.
|
|
98
|
+
# This is especially recommended for binary packages to ensure reproducibility, and is more
|
|
99
|
+
# commonly ignored for libraries.
|
|
100
|
+
# uv.lock
|
|
101
|
+
|
|
102
|
+
# poetry
|
|
103
|
+
# Similar to Pipfile.lock, it is generally recommended to include poetry.lock in version control.
|
|
104
|
+
# This is especially recommended for binary packages to ensure reproducibility, and is more
|
|
105
|
+
# commonly ignored for libraries.
|
|
106
|
+
# https://python-poetry.org/docs/basic-usage/#commit-your-poetrylock-file-to-version-control
|
|
107
|
+
# poetry.lock
|
|
108
|
+
# poetry.toml
|
|
109
|
+
|
|
110
|
+
# pdm
|
|
111
|
+
# Similar to Pipfile.lock, it is generally recommended to include pdm.lock in version control.
|
|
112
|
+
# pdm recommends including project-wide configuration in pdm.toml, but excluding .pdm-python.
|
|
113
|
+
# https://pdm-project.org/en/latest/usage/project/#working-with-version-control
|
|
114
|
+
# pdm.lock
|
|
115
|
+
# pdm.toml
|
|
116
|
+
.pdm-python
|
|
117
|
+
.pdm-build/
|
|
118
|
+
|
|
119
|
+
# pixi
|
|
120
|
+
# Similar to Pipfile.lock, it is generally recommended to include pixi.lock in version control.
|
|
121
|
+
# pixi.lock
|
|
122
|
+
# Pixi creates a virtual environment in the .pixi directory, just like venv module creates one
|
|
123
|
+
# in the .venv directory. It is recommended not to include this directory in version control.
|
|
124
|
+
.pixi
|
|
125
|
+
|
|
126
|
+
# PEP 582; used by e.g. github.com/David-OConnor/pyflow and github.com/pdm-project/pdm
|
|
127
|
+
__pypackages__/
|
|
128
|
+
|
|
129
|
+
# Celery stuff
|
|
130
|
+
celerybeat-schedule
|
|
131
|
+
celerybeat.pid
|
|
132
|
+
|
|
133
|
+
# Redis
|
|
134
|
+
*.rdb
|
|
135
|
+
*.aof
|
|
136
|
+
*.pid
|
|
137
|
+
|
|
138
|
+
# RabbitMQ
|
|
139
|
+
mnesia/
|
|
140
|
+
rabbitmq/
|
|
141
|
+
rabbitmq-data/
|
|
142
|
+
|
|
143
|
+
# ActiveMQ
|
|
144
|
+
activemq-data/
|
|
145
|
+
|
|
146
|
+
# SageMath parsed files
|
|
147
|
+
*.sage.py
|
|
148
|
+
|
|
149
|
+
# Environments
|
|
150
|
+
.env
|
|
151
|
+
.envrc
|
|
152
|
+
.venv
|
|
153
|
+
env/
|
|
154
|
+
venv/
|
|
155
|
+
ENV/
|
|
156
|
+
env.bak/
|
|
157
|
+
venv.bak/
|
|
158
|
+
|
|
159
|
+
# Spyder project settings
|
|
160
|
+
.spyderproject
|
|
161
|
+
.spyproject
|
|
162
|
+
|
|
163
|
+
# Rope project settings
|
|
164
|
+
.ropeproject
|
|
165
|
+
|
|
166
|
+
# mkdocs documentation
|
|
167
|
+
/site
|
|
168
|
+
|
|
169
|
+
# mypy
|
|
170
|
+
.mypy_cache/
|
|
171
|
+
.dmypy.json
|
|
172
|
+
dmypy.json
|
|
173
|
+
|
|
174
|
+
# Pyre type checker
|
|
175
|
+
.pyre/
|
|
176
|
+
|
|
177
|
+
# pytype static type analyzer
|
|
178
|
+
.pytype/
|
|
179
|
+
|
|
180
|
+
# Cython debug symbols
|
|
181
|
+
cython_debug/
|
|
182
|
+
|
|
183
|
+
# PyCharm
|
|
184
|
+
# JetBrains specific template is maintained in a separate JetBrains.gitignore that can
|
|
185
|
+
# be found at https://github.com/github/gitignore/blob/main/Global/JetBrains.gitignore
|
|
186
|
+
# and can be added to the global gitignore or merged into this file. For a more nuclear
|
|
187
|
+
# option (not recommended) you can uncomment the following to ignore the entire idea folder.
|
|
188
|
+
# .idea/
|
|
189
|
+
|
|
190
|
+
# Abstra
|
|
191
|
+
# Abstra is an AI-powered process automation framework.
|
|
192
|
+
# Ignore directories containing user credentials, local state, and settings.
|
|
193
|
+
# Learn more at https://abstra.io/docs
|
|
194
|
+
.abstra/
|
|
195
|
+
|
|
196
|
+
# Visual Studio Code
|
|
197
|
+
# Visual Studio Code specific template is maintained in a separate VisualStudioCode.gitignore
|
|
198
|
+
# that can be found at https://github.com/github/gitignore/blob/main/Global/VisualStudioCode.gitignore
|
|
199
|
+
# and can be added to the global gitignore or merged into this file. However, if you prefer,
|
|
200
|
+
# you could uncomment the following to ignore the entire vscode folder
|
|
201
|
+
# .vscode/
|
|
202
|
+
# Temporary file for partial code execution
|
|
203
|
+
tempCodeRunnerFile.py
|
|
204
|
+
|
|
205
|
+
# Ruff stuff:
|
|
206
|
+
.ruff_cache/
|
|
207
|
+
|
|
208
|
+
# PyPI configuration file
|
|
209
|
+
.pypirc
|
|
210
|
+
|
|
211
|
+
# Marimo
|
|
212
|
+
marimo/_static/
|
|
213
|
+
marimo/_lsp/
|
|
214
|
+
__marimo__/
|
|
215
|
+
|
|
216
|
+
# Streamlit
|
|
217
|
+
.streamlit/secrets.toml
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: structuretoolkit
|
|
3
|
-
Version: 0.0.
|
|
3
|
+
Version: 0.0.44
|
|
4
4
|
Summary: build, analyse and visualise atomistic structures for materials science
|
|
5
5
|
Project-URL: Homepage, https://github.com/pyiron/structuretoolkit
|
|
6
6
|
Project-URL: Documentation, https://github.com/pyiron/structuretoolkit
|
|
@@ -41,14 +41,13 @@ Classifier: Development Status :: 5 - Production/Stable
|
|
|
41
41
|
Classifier: Intended Audience :: Science/Research
|
|
42
42
|
Classifier: License :: OSI Approved :: BSD License
|
|
43
43
|
Classifier: Operating System :: OS Independent
|
|
44
|
-
Classifier: Programming Language :: Python :: 3.10
|
|
45
44
|
Classifier: Programming Language :: Python :: 3.11
|
|
46
45
|
Classifier: Programming Language :: Python :: 3.12
|
|
47
46
|
Classifier: Programming Language :: Python :: 3.13
|
|
48
47
|
Classifier: Topic :: Scientific/Engineering :: Physics
|
|
49
48
|
Requires-Python: <3.15,>=3.10
|
|
50
|
-
Requires-Dist: ase<=3.28.0,>=3.
|
|
51
|
-
Requires-Dist: numpy<=2.4.
|
|
49
|
+
Requires-Dist: ase<=3.28.0,>=3.24.0
|
|
50
|
+
Requires-Dist: numpy<=2.4.6,>=1.23.5
|
|
52
51
|
Requires-Dist: scipy<=1.17.1,>=1.15.0
|
|
53
52
|
Provides-Extra: clusters
|
|
54
53
|
Requires-Dist: scikit-learn==1.8.0; extra == 'clusters'
|
|
@@ -56,23 +55,23 @@ Provides-Extra: dscribe
|
|
|
56
55
|
Requires-Dist: dscribe==2.1.2; extra == 'dscribe'
|
|
57
56
|
Provides-Extra: grainboundary
|
|
58
57
|
Requires-Dist: aimsgb<=1.1.1,>=1.0.2; extra == 'grainboundary'
|
|
59
|
-
Requires-Dist: pymatgen
|
|
58
|
+
Requires-Dist: pymatgen==2026.3.23; extra == 'grainboundary'
|
|
60
59
|
Provides-Extra: matplotlib
|
|
61
|
-
Requires-Dist: matplotlib==3.10.
|
|
60
|
+
Requires-Dist: matplotlib==3.10.9; extra == 'matplotlib'
|
|
62
61
|
Provides-Extra: mp-api
|
|
63
62
|
Requires-Dist: mp-api==0.45.15; extra == 'mp-api'
|
|
64
|
-
Requires-Dist: pymatgen
|
|
63
|
+
Requires-Dist: pymatgen==2026.3.23; extra == 'mp-api'
|
|
65
64
|
Provides-Extra: nglview
|
|
66
65
|
Requires-Dist: nglview<=4.0.1,>=2.7.7; extra == 'nglview'
|
|
67
66
|
Provides-Extra: phonopy
|
|
68
|
-
Requires-Dist: phonopy<=
|
|
67
|
+
Requires-Dist: phonopy<=4.0.1,>=2.21.2; extra == 'phonopy'
|
|
69
68
|
Requires-Dist: spglib==2.7.0; extra == 'phonopy'
|
|
70
69
|
Provides-Extra: plotly
|
|
71
|
-
Requires-Dist: plotly<=6.
|
|
70
|
+
Requires-Dist: plotly<=6.8.0,>=6.0.0; extra == 'plotly'
|
|
72
71
|
Provides-Extra: pyscal
|
|
73
72
|
Requires-Dist: pyscal3<=3.3.2,>=3.2.5; extra == 'pyscal'
|
|
74
73
|
Provides-Extra: surface
|
|
75
|
-
Requires-Dist: pymatgen
|
|
74
|
+
Requires-Dist: pymatgen==2026.3.23; extra == 'surface'
|
|
76
75
|
Requires-Dist: spglib==2.7.0; extra == 'surface'
|
|
77
76
|
Provides-Extra: symmetry
|
|
78
77
|
Requires-Dist: spglib==2.7.0; extra == 'symmetry'
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
[build-system]
|
|
2
|
-
requires = ["ase", "numpy", "scipy", "hatchling==1.
|
|
2
|
+
requires = ["ase", "numpy", "scipy", "hatchling==1.30.1", "hatch-vcs==0.5.0"]
|
|
3
3
|
build-backend = "hatchling.build"
|
|
4
4
|
|
|
5
5
|
[project]
|
|
@@ -18,14 +18,13 @@ classifiers = [
|
|
|
18
18
|
"License :: OSI Approved :: BSD License",
|
|
19
19
|
"Intended Audience :: Science/Research",
|
|
20
20
|
"Operating System :: OS Independent",
|
|
21
|
-
"Programming Language :: Python :: 3.10",
|
|
22
21
|
"Programming Language :: Python :: 3.11",
|
|
23
22
|
"Programming Language :: Python :: 3.12",
|
|
24
23
|
"Programming Language :: Python :: 3.13",
|
|
25
24
|
]
|
|
26
25
|
dependencies = [
|
|
27
|
-
"ase>=3.
|
|
28
|
-
"numpy>=1.23.5,<=2.4.
|
|
26
|
+
"ase>=3.24.0,<=3.28.0",
|
|
27
|
+
"numpy>=1.23.5,<=2.4.6",
|
|
29
28
|
"scipy>=1.15.0,<=1.17.1",
|
|
30
29
|
]
|
|
31
30
|
dynamic = ["version"]
|
|
@@ -39,25 +38,25 @@ Repository = "https://github.com/pyiron/structuretoolkit"
|
|
|
39
38
|
dscribe = ["dscribe==2.1.2"]
|
|
40
39
|
grainboundary = [
|
|
41
40
|
"aimsgb>=1.0.2,<=1.1.1",
|
|
42
|
-
"pymatgen
|
|
41
|
+
"pymatgen==2026.3.23",
|
|
43
42
|
]
|
|
44
43
|
pyscal = ["pyscal3>=3.2.5,<=3.3.2"]
|
|
45
44
|
nglview = ["nglview>=2.7.7,<=4.0.1"]
|
|
46
|
-
matplotlib = ["matplotlib==3.10.
|
|
47
|
-
plotly = ["plotly>=
|
|
45
|
+
matplotlib = ["matplotlib==3.10.9"]
|
|
46
|
+
plotly = ["plotly>=6.0.0,<=6.8.0"]
|
|
48
47
|
clusters = ["scikit-learn==1.8.0"]
|
|
49
48
|
symmetry = ["spglib==2.7.0"]
|
|
50
49
|
surface = [
|
|
51
50
|
"spglib==2.7.0",
|
|
52
|
-
"pymatgen
|
|
51
|
+
"pymatgen==2026.3.23",
|
|
53
52
|
]
|
|
54
53
|
phonopy = [
|
|
55
|
-
"phonopy>=2.
|
|
54
|
+
"phonopy>=2.21.2,<=4.0.1",
|
|
56
55
|
"spglib==2.7.0",
|
|
57
56
|
]
|
|
58
57
|
mp-api = [
|
|
59
58
|
"mp-api==0.45.15",
|
|
60
|
-
"pymatgen
|
|
59
|
+
"pymatgen==2026.3.23",
|
|
61
60
|
]
|
|
62
61
|
|
|
63
62
|
[tool.ruff]
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
# file generated by vcs-versioning
|
|
2
|
+
# don't change, don't track in version control
|
|
3
|
+
from __future__ import annotations
|
|
4
|
+
|
|
5
|
+
__all__ = [
|
|
6
|
+
"__version__",
|
|
7
|
+
"__version_tuple__",
|
|
8
|
+
"version",
|
|
9
|
+
"version_tuple",
|
|
10
|
+
"__commit_id__",
|
|
11
|
+
"commit_id",
|
|
12
|
+
]
|
|
13
|
+
|
|
14
|
+
version: str
|
|
15
|
+
__version__: str
|
|
16
|
+
__version_tuple__: tuple[int | str, ...]
|
|
17
|
+
version_tuple: tuple[int | str, ...]
|
|
18
|
+
commit_id: str | None
|
|
19
|
+
__commit_id__: str | None
|
|
20
|
+
|
|
21
|
+
__version__ = version = '0.0.44'
|
|
22
|
+
__version_tuple__ = version_tuple = (0, 0, 44)
|
|
23
|
+
|
|
24
|
+
__commit_id__ = commit_id = None
|
|
@@ -11,7 +11,7 @@ def soap_descriptor_per_atom(
|
|
|
11
11
|
rbf: str = "gto",
|
|
12
12
|
weighting: np.ndarray | None = None,
|
|
13
13
|
average: str = "off",
|
|
14
|
-
compression: dict = None,
|
|
14
|
+
compression: dict | None = None,
|
|
15
15
|
species: list | None = None,
|
|
16
16
|
periodic: bool = True,
|
|
17
17
|
sparse: bool = False,
|
{structuretoolkit-0.0.42 → structuretoolkit-0.0.44}/src/structuretoolkit/analyse/neighbors.py
RENAMED
|
@@ -3,6 +3,7 @@
|
|
|
3
3
|
|
|
4
4
|
import itertools
|
|
5
5
|
import warnings
|
|
6
|
+
from typing import Any, cast
|
|
6
7
|
|
|
7
8
|
import numpy as np
|
|
8
9
|
from ase.atoms import Atoms
|
|
@@ -56,18 +57,18 @@ class Tree:
|
|
|
56
57
|
Args:
|
|
57
58
|
ref_structure (ase.atoms.Atoms): Reference structure.
|
|
58
59
|
"""
|
|
59
|
-
self._distances = None
|
|
60
|
-
self._vectors = None
|
|
61
|
-
self._indices = None
|
|
60
|
+
self._distances: Any = None
|
|
61
|
+
self._vectors: Any = None
|
|
62
|
+
self._indices: Any = None
|
|
62
63
|
self._mode = {"filled": True, "ragged": False, "flattened": False}
|
|
63
|
-
self._extended_positions = None
|
|
64
|
-
self._positions = None
|
|
65
|
-
self._wrapped_indices = None
|
|
66
|
-
self._extended_indices = None
|
|
64
|
+
self._extended_positions: Any = None
|
|
65
|
+
self._positions: Any = None
|
|
66
|
+
self._wrapped_indices: Any = None
|
|
67
|
+
self._extended_indices: Any = None
|
|
67
68
|
self._ref_structure = ref_structure.copy()
|
|
68
69
|
self.wrap_positions = False
|
|
69
|
-
self._tree = None
|
|
70
|
-
self.num_neighbors = None
|
|
70
|
+
self._tree: Any = None
|
|
71
|
+
self.num_neighbors: int | None = None
|
|
71
72
|
self.cutoff_radius = np.inf
|
|
72
73
|
self._norm_order = 2
|
|
73
74
|
|
|
@@ -91,6 +92,7 @@ class Tree:
|
|
|
91
92
|
for k, v in self._mode.items():
|
|
92
93
|
if v:
|
|
93
94
|
return k
|
|
95
|
+
raise ValueError("No neighbor representation mode is active")
|
|
94
96
|
|
|
95
97
|
def _set_mode(self, new_mode: str) -> None:
|
|
96
98
|
"""
|
|
@@ -172,6 +174,7 @@ class Tree:
|
|
|
172
174
|
return self._contract(value, ref_vector=ref_vector)
|
|
173
175
|
elif key == "flattened":
|
|
174
176
|
return value[self._distances < np.inf]
|
|
177
|
+
raise ValueError(f"Unknown neighbor representation mode: {key}")
|
|
175
178
|
|
|
176
179
|
@property
|
|
177
180
|
def distances(self) -> np.ndarray:
|
|
@@ -257,7 +260,7 @@ class Tree:
|
|
|
257
260
|
+ " with the correct norm_order value"
|
|
258
261
|
)
|
|
259
262
|
|
|
260
|
-
def _get_max_length(self, ref_vector: np.ndarray | None = None) -> int:
|
|
263
|
+
def _get_max_length(self, ref_vector: np.ndarray | None = None) -> int | None:
|
|
261
264
|
"""
|
|
262
265
|
Get the maximum length of the reference vector.
|
|
263
266
|
|
|
@@ -277,9 +280,7 @@ class Tree:
|
|
|
277
280
|
return None
|
|
278
281
|
return max(len(dd[dd < np.inf]) for dd in ref_vector)
|
|
279
282
|
|
|
280
|
-
def _contract(
|
|
281
|
-
self, value: np.ndarray, ref_vector: np.ndarray | None = None
|
|
282
|
-
) -> np.ndarray:
|
|
283
|
+
def _contract(self, value: np.ndarray, ref_vector: np.ndarray | None = None):
|
|
283
284
|
"""
|
|
284
285
|
Contract the given value based on the specified reference vector.
|
|
285
286
|
|
|
@@ -297,7 +298,7 @@ class Tree:
|
|
|
297
298
|
for vv, dist in zip(value, self.filled.distances, strict=True)
|
|
298
299
|
]
|
|
299
300
|
|
|
300
|
-
def _allow_ragged_to_mode(self, new_bool: bool) -> str:
|
|
301
|
+
def _allow_ragged_to_mode(self, new_bool: bool | None) -> str:
|
|
301
302
|
"""
|
|
302
303
|
Set the representation mode based on the value of new_bool.
|
|
303
304
|
|
|
@@ -504,6 +505,8 @@ class Tree:
|
|
|
504
505
|
if self.num_neighbors is None:
|
|
505
506
|
self.num_neighbors = num_neighbors
|
|
506
507
|
self.cutoff_radius = cutoff_radius
|
|
508
|
+
assert num_neighbors is not None
|
|
509
|
+
assert self.num_neighbors is not None
|
|
507
510
|
if num_neighbors > self.num_neighbors:
|
|
508
511
|
warnings.warn(
|
|
509
512
|
"Taking a larger search area after initialization has the risk of "
|
|
@@ -582,7 +585,7 @@ class Tree:
|
|
|
582
585
|
def _get_neighborhood(
|
|
583
586
|
self,
|
|
584
587
|
positions: np.ndarray,
|
|
585
|
-
num_neighbors: int = 12,
|
|
588
|
+
num_neighbors: int | None = 12,
|
|
586
589
|
cutoff_radius: float = np.inf,
|
|
587
590
|
exclude_self: bool = False,
|
|
588
591
|
width_buffer: float = 1.2,
|
|
@@ -611,7 +614,7 @@ class Tree:
|
|
|
611
614
|
cutoff_radius=cutoff_radius,
|
|
612
615
|
width_buffer=width_buffer,
|
|
613
616
|
)
|
|
614
|
-
if num_neighbors is not None:
|
|
617
|
+
if num_neighbors is not None and self.num_neighbors is not None:
|
|
615
618
|
self.num_neighbors -= 1
|
|
616
619
|
max_column = np.sum(distances < np.inf, axis=-1).max()
|
|
617
620
|
self._distances = distances[..., start_column:max_column]
|
|
@@ -620,7 +623,7 @@ class Tree:
|
|
|
620
623
|
self._positions = positions
|
|
621
624
|
return self
|
|
622
625
|
|
|
623
|
-
def _check_width(self, width: float, pbc:
|
|
626
|
+
def _check_width(self, width: float, pbc: np.ndarray) -> bool:
|
|
624
627
|
"""
|
|
625
628
|
Check if the width of the layer exceeds the specified value.
|
|
626
629
|
|
|
@@ -706,26 +709,19 @@ class Tree:
|
|
|
706
709
|
radius. For automated uses, see Atoms.analyse.pyscal_steinhardt_parameter()
|
|
707
710
|
"""
|
|
708
711
|
random_rotation = Rotation.from_mrp(np.random.random(3)).as_matrix()
|
|
709
|
-
|
|
710
|
-
|
|
711
|
-
|
|
712
|
-
|
|
713
|
-
|
|
714
|
-
|
|
715
|
-
|
|
716
|
-
|
|
717
|
-
l=l,
|
|
718
|
-
m=m,
|
|
719
|
-
cutoff_radius=cutoff_radius,
|
|
720
|
-
rotation=random_rotation,
|
|
721
|
-
)
|
|
722
|
-
)
|
|
723
|
-
** 2
|
|
724
|
-
for m in np.arange(-l, l + 1)
|
|
725
|
-
],
|
|
726
|
-
axis=0,
|
|
712
|
+
harmonic_values: list[np.ndarray] = [
|
|
713
|
+
np.absolute(
|
|
714
|
+
self.get_spherical_harmonics(
|
|
715
|
+
l=l,
|
|
716
|
+
m=m,
|
|
717
|
+
cutoff_radius=cutoff_radius,
|
|
718
|
+
rotation=random_rotation,
|
|
719
|
+
)
|
|
727
720
|
)
|
|
728
|
-
|
|
721
|
+
** 2
|
|
722
|
+
for m in np.arange(-l, l + 1)
|
|
723
|
+
]
|
|
724
|
+
return np.sqrt(4 * np.pi / (2 * l + 1) * np.sum(harmonic_values, axis=0))
|
|
729
725
|
|
|
730
726
|
@staticmethod
|
|
731
727
|
def _get_all_possible_pairs(l: int) -> np.ndarray:
|
|
@@ -827,8 +823,8 @@ class Neighbors(Tree):
|
|
|
827
823
|
"""
|
|
828
824
|
super().__init__(ref_structure=ref_structure)
|
|
829
825
|
self._tolerance = tolerance
|
|
830
|
-
self._cluster_vecs = None
|
|
831
|
-
self._cluster_dist = None
|
|
826
|
+
self._cluster_vecs: Any = None
|
|
827
|
+
self._cluster_dist: Any = None
|
|
832
828
|
|
|
833
829
|
def __repr__(self):
|
|
834
830
|
"""
|
|
@@ -1072,7 +1068,7 @@ class Neighbors(Tree):
|
|
|
1072
1068
|
|
|
1073
1069
|
def find_neighbors_by_vector(
|
|
1074
1070
|
self, vector: np.ndarray, return_deviation: bool = False
|
|
1075
|
-
) -> np.ndarray:
|
|
1071
|
+
) -> np.ndarray | tuple[np.ndarray, np.ndarray]:
|
|
1076
1072
|
"""
|
|
1077
1073
|
Args:
|
|
1078
1074
|
vector (list/np.ndarray): vector by which positions are translated (and neighbors are searched)
|
|
@@ -1323,9 +1319,9 @@ class Neighbors(Tree):
|
|
|
1323
1319
|
ind_shell = []
|
|
1324
1320
|
for d, i in zip(dist, ind, strict=True):
|
|
1325
1321
|
id_list = get_cluster(d[d < radius], i[d < radius])
|
|
1326
|
-
ia_shells_dict = {}
|
|
1322
|
+
ia_shells_dict: dict[str, list[list[int]]] = {}
|
|
1327
1323
|
for i_shell_list in id_list:
|
|
1328
|
-
ia_shell_dict = {}
|
|
1324
|
+
ia_shell_dict: dict[str, list[int]] = {}
|
|
1329
1325
|
for i_s in i_shell_list:
|
|
1330
1326
|
el = el_list[i_s]
|
|
1331
1327
|
if el not in ia_shell_dict:
|
|
@@ -1382,14 +1378,17 @@ def get_neighbors(
|
|
|
1382
1378
|
Returns:
|
|
1383
1379
|
Neighbors: An instance of the Neighbors class with the neighbor indices, distances, and vectors.
|
|
1384
1380
|
"""
|
|
1385
|
-
neigh =
|
|
1386
|
-
|
|
1387
|
-
|
|
1388
|
-
|
|
1389
|
-
|
|
1390
|
-
|
|
1391
|
-
|
|
1392
|
-
|
|
1381
|
+
neigh = cast(
|
|
1382
|
+
Neighbors,
|
|
1383
|
+
_get_neighbors(
|
|
1384
|
+
structure=structure,
|
|
1385
|
+
num_neighbors=num_neighbors,
|
|
1386
|
+
tolerance=tolerance,
|
|
1387
|
+
id_list=id_list,
|
|
1388
|
+
cutoff_radius=cutoff_radius,
|
|
1389
|
+
width_buffer=width_buffer,
|
|
1390
|
+
norm_order=norm_order,
|
|
1391
|
+
),
|
|
1393
1392
|
)
|
|
1394
1393
|
neigh._set_mode(mode)
|
|
1395
1394
|
return neigh
|
|
@@ -27,7 +27,7 @@ def get_steinhardt_parameters(
|
|
|
27
27
|
n_clusters: int | None = 2,
|
|
28
28
|
q: tuple | None = None,
|
|
29
29
|
averaged: bool = False,
|
|
30
|
-
) ->
|
|
30
|
+
) -> np.ndarray | tuple[np.ndarray, np.ndarray]:
|
|
31
31
|
"""
|
|
32
32
|
Calculate Steinhardts parameters
|
|
33
33
|
|
|
@@ -162,7 +162,7 @@ def get_diamond_structure_descriptors(
|
|
|
162
162
|
|
|
163
163
|
def get_adaptive_cna_descriptors(
|
|
164
164
|
structure: Atoms, mode: str = "total", ovito_compatibility: bool = False
|
|
165
|
-
) -> np.ndarray:
|
|
165
|
+
) -> dict | np.ndarray:
|
|
166
166
|
"""
|
|
167
167
|
Use common neighbor analysis
|
|
168
168
|
|
|
@@ -63,7 +63,7 @@ def get_snap_descriptors_per_atom(
|
|
|
63
63
|
structure: Atoms,
|
|
64
64
|
atom_types: list[str],
|
|
65
65
|
twojmax: int = 6,
|
|
66
|
-
element_radius: list[
|
|
66
|
+
element_radius: list[float] | None = None,
|
|
67
67
|
rcutfac: float = 1.0,
|
|
68
68
|
rfac0: float = 0.99363,
|
|
69
69
|
rmin0: float = 0.0,
|
|
@@ -114,7 +114,7 @@ def get_snap_descriptor_derivatives(
|
|
|
114
114
|
structure: Atoms,
|
|
115
115
|
atom_types: list[str],
|
|
116
116
|
twojmax: int = 6,
|
|
117
|
-
element_radius: list[
|
|
117
|
+
element_radius: list[float] | None = None,
|
|
118
118
|
rcutfac: float = 1.0,
|
|
119
119
|
rfac0: float = 0.99363,
|
|
120
120
|
rmin0: float = 0.0,
|
|
@@ -161,7 +161,7 @@ def get_snap_descriptor_derivatives(
|
|
|
161
161
|
)
|
|
162
162
|
|
|
163
163
|
|
|
164
|
-
def get_snap_descriptor_names(twojmax: int) ->
|
|
164
|
+
def get_snap_descriptor_names(twojmax: int) -> list[list[float]]:
|
|
165
165
|
"""
|
|
166
166
|
Get names of the SNAP descriptors
|
|
167
167
|
|
|
@@ -548,7 +548,7 @@ def _extract_computes_snap(
|
|
|
548
548
|
np.ndarray: Output of the LAMMPS compute command
|
|
549
549
|
"""
|
|
550
550
|
lmp_atom_ids = lmp.numpy.extract_atom_iarray("id", num_atoms).flatten()
|
|
551
|
-
cond = np.all(lmp_atom_ids == 1 + np.arange(num_atoms))
|
|
551
|
+
cond = bool(np.all(lmp_atom_ids == 1 + np.arange(num_atoms)))
|
|
552
552
|
assert cond, "LAMMPS seems to have lost atoms"
|
|
553
553
|
|
|
554
554
|
# Extract types
|
|
@@ -556,7 +556,7 @@ def _extract_computes_snap(
|
|
|
556
556
|
lmp_volume = lmp.get_thermo("vol")
|
|
557
557
|
|
|
558
558
|
# Extract Bsum
|
|
559
|
-
_extract_compute_np(lmp, "b_sum", 0, 1, (n_coeff))
|
|
559
|
+
_extract_compute_np(lmp, "b_sum", 0, 1, (n_coeff,))
|
|
560
560
|
|
|
561
561
|
# Extract B
|
|
562
562
|
lmp_barr = _extract_compute_np(lmp, "b", 1, 2, (num_atoms, n_coeff))
|
|
@@ -571,13 +571,13 @@ def _extract_computes_snap(
|
|
|
571
571
|
|
|
572
572
|
lmp_dbarr = _extract_compute_np(lmp, "db", 1, 2, (num_atoms, num_types, 3, n_coeff))
|
|
573
573
|
lmp_dbsum = _extract_compute_np(lmp, "db_sum", 0, 1, (num_types, 3, n_coeff))
|
|
574
|
-
cond = np.allclose(lmp_dbsum, lmp_dbarr.sum(axis=0), rtol=1e-12, atol=1e-12)
|
|
574
|
+
cond = bool(np.allclose(lmp_dbsum, lmp_dbarr.sum(axis=0), rtol=1e-12, atol=1e-12))
|
|
575
575
|
assert cond, "db_sum doesn't match sum of db"
|
|
576
576
|
db_atom = np.transpose(lmp_dbarr, (0, 2, 1, 3))
|
|
577
577
|
|
|
578
578
|
lmp_vbarr = _extract_compute_np(lmp, "vb", 1, 2, (num_atoms, num_types, 6, n_coeff))
|
|
579
579
|
lmp_vbsum = _extract_compute_np(lmp, "vb_sum", 0, 1, (num_types, 6, n_coeff))
|
|
580
|
-
cond = np.allclose(lmp_vbsum, lmp_vbarr.sum(axis=0), rtol=1e-12, atol=1e-12)
|
|
580
|
+
cond = bool(np.allclose(lmp_vbsum, lmp_vbarr.sum(axis=0), rtol=1e-12, atol=1e-12))
|
|
581
581
|
assert cond, "vb_sum doesn't match sum of vb"
|
|
582
582
|
vb_sum = np.transpose(lmp_vbsum, (1, 0, 2)) / lmp_volume * eV_div_A3_to_bar
|
|
583
583
|
|