Analyses by user programs¶
In this tutorial, we will write a user program using odatse-SXRD module and perform analyese. As an example, we adopt Nelder-Mead method for the inverse problem algorithm.
Location of the sample files¶
The sample files are located in sample/user_program
.
The following files are stored in the folder.
simple.py
Source file of the main program. This program reads
input.toml
for the parameters.input.toml
Input file of the main program.
sic111-r3xr3.blk
,sic111-r3xr3_f.dat
Reference files to proceed with calculations in the main program.
ref_res.txt
,ref_SimplexData.txt
The files containing the answers you want to seek in this tutorial.
simple2.py
Another version of source file of the main program. The parameters are embedded in the program as a dict.
The following sections describe these files and then show the actual calculation results.
Description of main program¶
simple.py
is a simple program for the analyses using odatse-SXRD module.
The entire source file is shown as follows:
import numpy as np
import odatse
import odatse.algorithm.min_search
from odatse.extra.SXRD import Solver
info = odatse.Info.from_file("input.toml")
solver = Solver(info)
runner = odatse.Runner(solver, info)
alg = odatse.algorithm.min_search.Algorithm(info, runner)
alg.main()
At the beginning of the program, the required modules are imported as listed below.
odatse
for the main module of ODAT-SE.odatse.algorithm.min_search
for the module of the inverse problem algorithm used in this tutorial.odatse.extra.SXRD
for the direct problem solver module.
Next, the instances of the classes are created.
odatse.Info
classThis class is for storing the parameters. It is created by calling a class method
from_file
with a path to TOML file as an argument.odatse.extra.SXRD.Solver
classThis class is for the direct problem solver of the odatse-SXRD module. It is created by passing an instance of Info class.
odatse.Runner
classThis class is for connecting the direct problem solver and the inverse problem algorithm. It is created by passing an instance of Solver class and an instance of Info class.
odatse.algorithm.min_search.Algorithm
classThis class is for the inverse problem algorithm. In this tutorial, we use
min_search
module that implements the optimization by Nelder-Mead method. It is created by passing an instance of Runner class.
After creating the instances of Solver, Runner, and Algorithm in this order, we invoke main()
method of the Algorithm class to start analyses.
In the above program, the input parameters are read from a file in TOML format. It is also possible to take the parameters in the form of dictionary.
simple2.py
is anther version of the main program in which the parameters are embedded in the program. The entire source file is shown below:
import numpy as np
import odatse
import odatse.algorithm.min_search
from odatse.extra.SXRD import Solver
param = {
"base": {
"dimension": 2,
"output_dir": "output",
},
"solver": {
"config": {
"sxrd_exec_file": "sxrdcalc",
"bulk_struc_in_file": "sic111-r3xr3.blk",
},
"param": {
"scale_factor": 1.0,
"type_vector": [1, 2],
"domain": [
{
"domain_occupancy": 1.0,
"atom": [
{
"name": "Si",
"pos_center": [0.00000000, 0.00000000, 1.00000000],
"DWfactor": 0.0,
"occupancy": 1.0,
"displace_vector": [[1, 0.0, 0.0, 1.0]]
},
{
"name": "Si",
"pos_center": [0.33333333, 0.66666667, 1.00000000],
"DWfactor": 0.0,
"occupancy": 1.0,
"displace_vector": [[1, 0.0, 0.0, 1.0]]
},
{
"name": "Si",
"pos_center": [0.66666667, 0.33333333, 1.00000000],
"DWfactor": 0.0,
"occupancy": 1.0,
"displace_vector": [[1, 0.0, 0.0, 1.0]]
},
{
"name": "Si",
"pos_center": [0.33333333, 0.33333333, 1.20000000],
"DWfactor": 0.0,
"occupancy": 1.0,
"displace_vector": [[2, 0.0, 0.0, 1.0]]
},
],
},
],
},
"reference": {
"f_in_file": "sic111-r3xr3_f.dat",
},
},
"algorithm": {
"label_list": ["z1", "z2"],
"param": {
"min_list": [-0.2, -0.2],
"max_list": [ 0.2, 0.2],
"initial_list": [ 0.0, 0.0 ],
},
},
}
info = odatse.Info(param)
solver = Solver(info)
runner = odatse.Runner(solver, info)
alg = odatse.algorithm.min_search.Algorithm(info, runner)
alg.main()
An instance of Info class is created by passing a set of parameters in a dict form. It is also possible to generate the parameters within the program before passing to the class.
Input files¶
The input file input.toml
for the main program is the same as that used in the previous tutorial for Nelder-Mead method.
Except, algorithm.name
parameter for specifying the algorithm type should be ignored.
The reference files are the same as those in the previous tutorials.
Calculation execution¶
First, move to the folder where the sample files are located. (We assume that you are directly under the directory where you downloaded this software.)
$ cd sample/user_program
Copy sxrdcalc
.
$ cp ../../sxrdcalc-main/sxrdcalc .
Run the main program. The computation time will take only a few seconds on a normal PC.
$ python3 simple.py | tee log.txt
The standard output will look as follows.
Optimization terminated successfully.
Current function value: 0.000106
Iterations: 26
Function evaluations: 53
iteration: 26
len(allvecs): 27
step: 0
allvecs[step]: [0. 0.]
step: 1
allvecs[step]: [0. 0.]
step: 2
allvecs[step]: [0. 0.]
...
z1
and z2
are the candidate parameters at each step, and R-factor
is the function value at that point.
The final estimated parameters will be written to output/res.dat
.
In the current case, the following result will be obtained:
fx = 0.000106
z1 = -2.351035891479114e-05
z2 = 0.025129315870799473
You can see that we will get the same values as the correct answer data in ref.txt
.