diff --git a/docs/source/conf.py b/docs/source/conf.py index b375175..0fdaee6 100644 --- a/docs/source/conf.py +++ b/docs/source/conf.py @@ -49,7 +49,9 @@ extensions = [ # One only works in 1.8+, the other is depricated in >1.8 autodoc_default_options = { - 'show-inheritance': True + 'show-inheritance': True, + 'special-members': '__init__', + 'member-order': 'bysource', } autodoc_default_flags = [ 'show-inheritance'] diff --git a/docs/source/intro.rst b/docs/source/intro.rst index 75fe622..2c3d5a4 100644 --- a/docs/source/intro.rst +++ b/docs/source/intro.rst @@ -17,6 +17,9 @@ CDTools is a python library for ptychography and CDI reconstructions, using an a # Load a data file dataset = Ptycho2DDataset.from_cxi('ptycho_data.cxi') + + # Look at the data inside + dataset.inspect() # Initialize a model from the data model = FancyPtycho.from_dataset(dataset) @@ -36,7 +39,16 @@ CDTools is a python library for ptychography and CDI reconstructions, using an a CDTools makes it simple to load and inspect data stored in .cxi files. Reconstruction models for common geometries are included "out of the box". For more advanced users, it includes a collection of differentiable functions which can beused to construct new forward models. -The high-level interface to CDTools - datasets and models - is built on a set oflower-level tools. These include functions for accessing stored data in .cxi files, tools to visualize data and reconstructions, and tools that implement basic operations - such as light propagation - relevant to coherent diffraction. These functions can be used alongside the high-level interface, when needed. +The high-level interface to CDTools - datasets and models - is built on a set of lower-level tools. These lower level tools include: -Enough blabber. If you're interested, read the docs! +- functions for accessing stored data in .cxi files +- plotting tools to visualize data and reconstructions +- basic operations, like light propagators, needed for coherent diffraction +- tools that implement basic operations - such as light propagation - relevant to coherent diffraction. +- analysis functions for assessing the quality of reconstructions + + +These functions can be used alongside the high-level interface to make fun and fancy reconstruction scripts for challenging data. + +If you're interested, read the docs! diff --git a/docs/source/models.rst b/docs/source/models.rst index 34b0ca8..65bf248 100644 --- a/docs/source/models.rst +++ b/docs/source/models.rst @@ -3,5 +3,5 @@ Models .. automodule:: cdtools.models :members: - :private-members: + diff --git a/docs/source/tools/analysis.rst b/docs/source/tools/analysis.rst index ff858d1..722dfdf 100644 --- a/docs/source/tools/analysis.rst +++ b/docs/source/tools/analysis.rst @@ -3,3 +3,4 @@ Analysis .. automodule:: cdtools.tools.analysis :members: + diff --git a/docs/source/tutorial.rst b/docs/source/tutorial.rst index 3b9fb71..1533e83 100644 --- a/docs/source/tutorial.rst +++ b/docs/source/tutorial.rst @@ -1,111 +1,15 @@ Tutorial ======== -WARNING: THE FOLLOWING TUTORIAL IS OUT OF DATE! It has some helpful information, but it is not trustworthy. Please rely on the examples, which are current as of February 2024. - -This tutorial builds on the examples, leading to a more complete understanding of how to use CDTools and - importantly - how to extend it. First, we will cover the details of writing a useful reconstruction script for a particular experiment. Next, we will discuss how to implement a new dataset type for different kinds of coherent diffraction. Finally, we will go over how to make new models to cover specific types of ptychography which aren't described by any of the built-in models. - - -Reconstruction Scripts ----------------------- - -In this section, we will write a script to run a reconstruction on a dataset collected from our benchtop optical ptychography playground. This mirrors very closely the reconstruction examples, however I encourage everyone to follow along, writing this script out line-by-line, to help you learn more permanently the process of writing a custom reconstruction script. - -Our first step will be creating the file and filling out the boilerplate: All the imports we'll need. - -.. code-block:: python - - import cdtools - from matplotlib import pyplot as plt - from scipy import io - - -You can always import more libraries, like numpy, or pytorch, or pandas, or what have you, as needed. Next, we load the dataset and give it a look-over - - -.. code-block:: python - - filename = 'example_data/lab_ptycho_data.cxi' - dataset = cdtools.datasets.Ptycho2DDataset.from_cxi(filename) - - dataset.inspect() - plt.show() - -Now, run this script! You should see a window pop up, showing a nanomap of the integrated intensities at each scan point on one side, and an individual diffraction pattern on the other. You can then click around to make sure that everything is in order. - -Now that we know we have the data loaded and it looks good, we can go ahead and comment out the dataset inspecting code, and move on to creating a model. It's usually a good idea to start by loading a standard :code:`FancyPtycho` model without any special changes, sending it to the GPU. - -.. code-block:: python - - model = cdtools.models.FancyPtycho.from_dataset(dataset) - model.to(device='cuda') - dataset.get_as(device='cuda') - - -We then try a basic Adam reconstruction with this model, with no changes to the defaults, to see how it works. - -.. code-block:: python - - for loss in model.Adam_optimize(50, dataset): - model.inspect(dataset) - print(model.report()) - - model.compare(dataset) - plt.show() - - -It is worth noting here exactly how this code is working. The reconstruction methods are actually returning generators. Generators in pythons are objects that work like lists, or tuples, but have to be read out one item at a time, from left to right. The catch is that, instead of just reading out objects from a list, they can run arbitrary code each time they are asked for the "next" item. - -In CDTools, every reconstruction method will return a generator. Whenever the generator is asked for the next item, it runs a single epoch of the reconstructionalgorithm, and then returns the average loss over that epoch as that next item. This allows the execution of the reconstruction algorithm to pause once every epoch, allowing some time for the user to run a small snippet of code to inspect how the reconstruction is coming along. - -From the end user perspective, all this means is: follow the format above, or more generally put the :code:`model.Adam_optimize(n, dataset)` call anywhere that you would feel comfortable putting a call to :code:`range(n)` - list comprehensions, for loops, etc. In this case, we have called a function to plot out the current state of the reconstruction, and a function to print out the current loss and iteration time. - -Once we run this, we can take a look at the result. What we see is pretty good, but we can see that there are some issues with the reconstruction near the edge, and the probe itself seems to be larger than the "stage" on which we're reconstructing it. So, we can make two tweaks to this code in response. First, we increase the oversampling ratio, which doubles the size of the stage (this often can cause other issues as well, but generally works well in situations like this where the probe is honestly too large. - -.. code-block:: python - - model = cdtools.models.FancyPtycho.from_dataset(dataset, oversampling=2) - - -And secondly, we note that there don't seem to be any errors with the positioning. So we can just not reconstruct the probe positions, knowing that the initial guesses are already accurate enough. We can do this by writing the following line, just before we run the reconstruction for loop. - -.. code-block:: python - - model.translation_offsets.requires_grad = False - -What is going on here is that, when running the optimization algorithm, pytorch will automatically calculate gradients for and then optimize over a number of parameters defined in the model - this includes parameters like :code:`model.probe`, :code:`model.obj`, :code:`model.background`, etc. We can tell pytorch to stop calculating gradients for (and stop updating) any of these parameters by setting their :code:`requires_grad` property to :code:`False`. - -After running this reconstruction, we can see that we're getting a little improvement (and a larger field of view) by using oversampling, but out in the corners we're nucleating extra probes! We can fix this by adding a probe support - that is, declating that the probe has to be defined only within a certain box. This can be done most easily with an argument to the model constructor: - -.. code-block:: python - - model = cdtools.models.FancyPtycho.from_dataset(dataset, oversampling=2, - probe_support_radius=90) - - -It also seems like we need a few more iterations to finish converging, so we up the iteration count to 100. - -.. code-block:: python - - for i, loss in enumerate(model.Adam_optimize(100, dataset)): - - -Now we expect to get a nice reconstruction, so we can save the data. You can save the data in any form you like, once the relevant information is extracted from the model and put into a dictionary. The standard method for saving out this information is as follows: - -.. code-block:: python - - io.savemat('example_reconstructions/lab_ptycho.pickle', - model.save_results(dataset)) - -This is usually placed before the call to :code:`plt.show()`, to make sure that if the user manually exits the program once all the plot windows are opened, the data will still have been saved. - -Now, your file should match the example file in examples/lab_ptycho_data.py. +The following tutorial gives a peek under the hood, and is intended for someone who might want to write their own variant of a ptychography model or modify an existing model to meet a specific need. If you just need to use CDTools for a reconstruction, or are just starting to work with the code, the examples section is a great first introduction. +In the first section of the tutorial, we will discuss how the datasets are defined and go through the process of defining a new dataset type. Following that, we will go through the process of defining a simplified model for standard ptychography. + Datasets -------- -In this section, we will write a bare-bones dataset class for 2D ptychography data to demonstrate the process of writing a new dataset class. At the end of the tutorial, we will have written the file examples/basic_ptycho_dataset.py, which can be consulted for reference. +In this section, we will write a bare-bones dataset class for 2D ptychography data to demonstrate the process of writing a new dataset class. At the end of the tutorial, we will have written the file examples/tutorial_basic_ptycho_dataset.py, which can be consulted for reference. Basic Idea ++++++++++ @@ -149,7 +53,7 @@ The next thing to implement is the initialization code. Here we can leverage som .. code-block:: python def __init__(self, *args, **kwargs): - super(BasicPtychoDataset,self).__init__(*args, **kwargs) + super().__init__(*args, **kwargs) Of course, there is also some data that are unique to this kind of dataset. In this case, those data are the probe translations and the measured diffraction patterns. Therefore, we extend this definition to the following: @@ -159,7 +63,7 @@ Of course, there is also some data that are unique to this kind of dataset. In t def __init__(self, translations, patterns, *args, **kwargs): """Initialize the dataset from python objects""" - super(BasicPtychoDataset,self).__init__(*args, **kwargs) + super().__init__(*args, **kwargs) self.translations = t.Tensor(translations).clone() self.patterns = t.Tensor(patterns).clone() @@ -187,7 +91,7 @@ Remember that it's not needed to worry about what device or datatype the data is def to(self, *args, **kwargs): """Sends the relevant data to the given device and dtype""" - super(BasicPtychoDataset,self).to(*args,**kwargs) + super().to(*args,**kwargs) self.translations = self.translations.to(*args, **kwargs) self.patterns = self.patterns.to(*args, **kwargs) @@ -228,7 +132,7 @@ Now to save the data, we override :code:`to_cxi()`, in a fairly self-explanatory def to_cxi(self, cxi_file): """Saves out a BasicPtychoDataset as a .cxi file""" - super(BasicPtychoDataset,self).to_cxi(cxi_file) + super().to_cxi(cxi_file) cdtdata.add_data(cxi_file, self.patterns, axes=self.axes) cdtdata.add_ptycho_translations(cxi_file, self.translations) @@ -259,17 +163,21 @@ This is a bare-bones class, set up to demonstrate the minimum neccessary to deve Models ------ -In this section, we will write a basic model for 2D ptychography reconstructions. At the end of this tutorial, we will have written the class defined in examples/simple_ptycho_model.py +In this section, we will write a basic model for 2D ptychography reconstructions. At the end of this tutorial, we will have written the class defined in examples/tutorial_simple_ptycho_model.py Basic Idea ++++++++++ -Just like CDTools Datasets subclass pytorch Datasets, CDTools models subclass pytorch modules (yes, I know they are different words - we use the word "model" in CDTools to conform to usage in the world of ptychography/CDI). The major difference is that the base CDTools models also contains a few standard methods to run automatic differentiation reconstructions on itself. This isn't necessarily the cleanest or most portable approach, but we've found that it feels very natural from the perspective of an end user interacting with the toolbox only through some basic reconstruction scripts. +Just like CDTools Datasets subclass pytorch Datasets, CDTools models subclass pytorch modules. However, the concept of a CDTools model does differ slightly from that of a pytorch module, because the CDTools models also contain a few standard methods to run automatic differentiation reconstructons on themselves. -The models themselves have a :code:`model.forward()` function which contains the real meat. In any CDTools model, this forward function takes in a set of parameters describing the specific diffraction pattern to simulate, and outputs a simulated diffraction pattern. The inputs could be as simple as a diffraction pattern index, or could explicitly include other information like the probe position. +This isn't necessarily the cleanest or most portable approach, but we've found that it feels very natural from the perspective of an end user interacting with the toolbox only through the reconstruction scripts. -In practice, the forward model is defined in the top level :code:`CDIModel` class from which all other models are derived. The definition is quite simple: +The heart of each model is a :code:`model.forward()` function. In any CDTools model, this forward function maps a set of parameters describing the specific diffraction pattern to simulate to the simulated result. When it's paired with an appropriate dataset for a reconstruction, it maps from the "inputs" defined by the dataset to the "outputs". + +For ptychography, this information is usually index of the exposure within the dataset (which is used to retrieve exposure-to-exposure information, like probe intensity factors) and the object translation. + +A simple forward model is defined in the top level :code:`CDIModel` class from which all other models are derived, and rarely needs to be overridden. The definition is quite simple: .. code-block:: python @@ -278,7 +186,7 @@ In practice, the forward model is defined in the top level :code:`CDIModel` clas So we can see that to fully implement this forward model, we have to define the three functions :code:`model.interaction()`, :code:`model.forward_propagator()`, and :code:`model.measurement()`, which simulate conceptual stages in the diffraction process. -Beyond the basic model definition, a few other tools need to be defined. The model has to be able to create itself from a dataset, has to have a loss function defined for use with automtic differentiation, has to know how to plot out it's progress, and has to be able to save out the results of a reconstruction. The details of how to implement all of this in a model are shown below. +In addition to the core model definition, a few other functions need to be defined to make the model useful. The model needs an *initializer* to create itself from a dataset, it must have an appropriate *loss function* defined for use with automtic differentiation, a way of plotting the progress of a reconstruction, and must know how to save the results of a reconstruction in a useful format. Writing the Skeleton @@ -288,16 +196,16 @@ Once again, we start with the basic skeleton .. code-block:: python - import numpy as np - import torch as t - from cdtools.models import CDIModel - from cdtools import tools + import torch as t + from cdtools.models import CDIModel + from cdtools import tools + from cdtools.tools import plotting as p __all__ = ['SimplePtycho'] class SimplePtycho(CDIModel): - """A simple ptychography model for exploring ideas and extensions""" - pass + """A simple ptychography model to demonstrate the structure of a model + """ Note that we imported the full tools package, as we will find ourselves using many low-level functions defined there to implement the model. @@ -305,101 +213,137 @@ Note that we imported the full tools package, as we will find ourselves using ma Initialization from Python ++++++++++++++++++++++++++ -Two initialization functions need to be written. First, we write the :code:`__init__()` function, which initializes the model from a collection of python objects describing the system. We then write an initializer that creates a model using a dataset to define the various parameters. +Two initialization functions need to be written. First, we write the :code:`__init__()` function, which initializes the model from a collection of python objects describing the system. We then write an initializer that creates a model using a dataset to initialize the various parameters. -It's important to note that there's not requirement for what the arguments to the initialization function of any particular model should be, only that they contain enough information to run the simulations! It should be chosen in a model-by-model way to allow for the most transparent code. +There is no requirement for what the arguments to the initialization function of any particular model should be, only that they contain enough information to run the simulations! It should be chosen in a model-by-model basis to allow for the most sensible code. .. code-block:: python - def __init__(self, probe_basis, probe_guess, obj_guess, - min_translation = [0,0]): + def __init__( + self, + wavelength, + probe_basis, + probe_guess, + obj_guess, + min_translation = [0,0], + ): + # We initialize the superclass + super().__init__() + + # We register all the constants, like wavelength, as buffers. This + # lets the model hook into some nice pytorch features, like using + # model.to, and broadcasting the model state across multiple GPUs + self.register_buffer('wavelength', t.as_tensor(wavelength)) + self.register_buffer('min_translation', t.as_tensor(min_translation)) + self.register_buffer('probe_basis', t.as_tensor(probe_basis)) + + # We cast the probe and object to 64-bit complex tensors + probe_guess = t.as_tensor(probe_guess, dtype=t.complex64) + obj_guess = t.as_tensor(obj_guess, dtype=t.complex64) + + # We rescale the probe here so it learns at the same rate as the + # object when using optimizers, like Adam, which set the stepsize + # to a fixed maximum + self.register_buffer('probe_norm', t.max(t.abs(probe_guess))) + + # And we store the probe and object guesses as parameters, so + # they can get optimized by pytorch + self.probe = t.nn.Parameter(probe_guess / self.probe_norm) + self.obj = t.nn.Parameter(obj_guess) - # We have to initialize the Module - super(SimplePtycho,self).__init__() - - # We first save the relevant information - self.min_translation = t.Tensor(min_translation) - self.probe_basis = t.Tensor(probe_basis) + +The first thing to notice about this model is that all the fixed, geometric information is stored with the :code:`module.register_buffer()` function. This is what makes it possible to move all the relevant tensors between devices using a single call to :code:`module.to()`, for example. It stores thetensor as an object attribute, but it also registers it so that pytorch is aware that this attribute helps to encode the state of the model. - # We rescale the probe so it learns at the same rate as the object - self.probe_norm = t.max(t.abs(probe_guess).to(t.float32)) - self.probe = t.nn.Parameter(probe_guess.to(t.complex64) - / self.probe_norm) - self.obj = t.nn.Parameter(obj_guess.to(t.complex64)) - +The supporting information we need is the wavelength of the illumination, the basis of the probe array in real space, and an offset to define the zero point of the translation. -Here, we chose to define the model based on a basis matrix describing the probe array, an initial guess at the probe, and an initial object. In addition, an optional offset for the translations is included. +The final two pieces of information that we need to save are the probe and object, and both of these get defined as :code:`t.nn.Parameter` objects instead of Tensors. As a result, they get registered as parameters in the pytorch module, and will therefore be optimized over in any later reconstructions. In addition, the :code:`requires_grad` flag is set to :code:`True`, which means that the information needed for gradient calculations will be stored on every Tensor that results from a calculation including a Parameter. -The first part of this initialization is quite straightforward - we create some tensors for the minimum translation and the probe basis. But then, the next two pieces of information that we save are defined as :code:`t.nn.Parameter` objects, not Tensors! Parameters are different from Tensors in two ways. +A list of all parameters associated with the module can be found by calling :code:`module.parameters()`. -The first way that they are different is that, by default, they have the :code:`requires_grad` flag set to :code:`True`, which means that the information needed for gradient calculations will be stored on every Tensor that results from a calculation including a Parameter. The second difference is that, when a Parameter is added to a Module, the Module adds that parameter to a list, which can be accessed by calling :code:`module.parameters()`. +Any additional targets of reconstruction - such as exposure-to-exposure illumination weights, translation offsets, or a detector background - would be added to the model as a parameter in a similar way. -The key here is that the model itself is subclassing a pytorch Module. So, every parameter that we will attempt to reconstruct, we add to the CDTools model as a Parameter. This way, the model automatically knows which variables to update with gradient descent, and which to keep as they are. Here, we only need to reconstruct the probe and object. +One final note is that we actually store a scaled version of the probe. This is a specific case of a general policy designed around making it easy to use the Adam optimizer. -One final note is that we actually store a scaled version of the probe. This is a hack. It is simply because the Adam optimization method, which is the most commonly used, uses learning rates that scale with the amplitude of the parameter, rather than with the amplitude of it's gradients. Unti pytorch implements separate parameter-group learning rates in Adam, rescaling all the parameters to have a typical amplitude near 1 is the best way to get well-behaved reconstructions. +The Adam optimizer is designed so that the learning rate sets the maximum stepsize which will be taken in any single iteration. Therefore, it is important to make sure that *all parameters of the model are of order unity*. To enable this, we scale the probe so that the typical pixel value within the probe array is of order 1. + +This is important to remember when adding additional error models. Rescaling all the parameters to have a typical amplitude near 1 is the best way to get well-behaved reconstructions. Initialization from Dataset +++++++++++++++++++++++++++ -To initialize the object from a dataset, we need to start by extracting the relevant information from the dataset. Then we can simply call the constructor we defined earlier. +To initialize the object from a dataset, we need to start by extracting the relevant information from the dataset, before calling the constructor we defined above: .. code-block:: python - + @classmethod def from_dataset(cls, dataset): - # First, load the information from the dataset + + # We get the key geometry information from the dataset wavelength = dataset.wavelength det_basis = dataset.detector_geometry['basis'] det_shape = dataset[0][1].shape distance = dataset.detector_geometry['distance'] - (indices, translations), patterns = dataset[:] - # Then, generate the probe geometry + # Then, we generate the probe geometry ewg = tools.initializers.exit_wave_geometry - probe_basis, probe_shape, det_slice = ewg(det_basis, - det_shape, - wavelength, - distance) + probe_basis = ewg(det_basis, det_shape, wavelength, distance) - # Next generate the object geometry + # Next generate the object geometry from the probe geometry and + # the translations + (indices, translations), patterns = dataset[:] pix_translations = tools.interactions.translations_to_pixel( - probe_basis, translations) + probe_basis, + translations, + ) obj_size, min_translation = tools.initializers.calc_object_setup( - probe_shape, pix_translations) + det_shape, + pix_translations, + ) - # Finally, initialize the probe and object using this information - probe = tools.initializers.SHARP_style_probe(dataset, - probe_shape, - det_slice) + # Finally, initialize the probe and object using this information + probe = tools.initializers.SHARP_style_probe(dataset) + obj = t.ones(obj_size).to(dtype=t.complex64) - obj = t.ones(obj_size, dtype=t.complex64) - - return cls(probe_basis, probe, obj, min_translation=min_translation) - + return cls( + wavelength, + probe_basis, + probe, + obj, + min_translation=min_translation + ) Here, we start by pulling the basic geometric information from the dataset. Then, we use a number of the basic tools to do calculations such as finding the probe basis from the detector geometry, or calculating how big our object array should be. -Once we have the basic setup ready, we then use one of the initialization functions - in this case, :code:`tools.initializers.SHARP_style_probe`, to find a sensible initialization for the probe. This particular initialization is based on the approach used in the SHARP package. Once all the needed information has been collected, we initialize the object. +Once we have the basic setup ready, we then use one of the initialization functions - in this case, :code:`tools.initializers.SHARP_style_probe`, to find a sensible initialization for the probe. This particular initialization is based on the approach used in the SHARP package, where the square-root of the mean diffraction pattern intensity is used to estimate the structure of the illumination at focus. + +Once all the needed information has been collected, we initialize the object. The Forward Model +++++++++++++++++ -First, we have to implement the interaction model. This function should take the inputs defining the specific diffraction pattern or collection of patterns, and return an exit wave or set of exit waves that would be expected from that set of inputs. This models the interaction of the probe with the sample +First, we have to implement the interaction model, as below: .. code-block:: python def interaction(self, index, translations): - pix_trans = tools.interactions.translations_to_pixel(self.probe_basis, - translations) + + # We map from real-space to pixel-space units + pix_trans = tools.interactions.translations_to_pixel( + self.probe_basis, + translations) pix_trans -= self.min_translation - return tools.interactions.ptycho_2D_round(self.probe_norm * self.probe, - self.obj, - pix_trans) + + # This function extracts the appropriate window from the object and + # multiplies the object and probe functions + return tools.interactions.ptycho_2D_round( + self.probe_norm * self.probe, + self.obj, + pix_trans) -Here, we take input in the form of an index and a translation. Note that this has to match the format that is output by the associated datasets that we will use for reconstruction. +Here, we take input in the form of an index and a translation. Note that this input format much match the format that is output by the associated datasets that we will use for reconstruction, in this case BasicPtychoDataset. We start by mapping the translation, given in real space, into pixel coordinates. Then, we use an "off-the-shelf" interaction model - :code:`ptycho_2d_round`, which models a standard 2D ptychography interaction, but rounds the translations to the nearest whole pixel (does not attempt subpixel translations). @@ -417,23 +361,7 @@ The next three definitions amount to just choosing an off-the-shelf function to return tools.losses.amplitude_mse(real_data, sim_data) -The forward propagator maps the exit wave to the wave at the surface of the detector, here using a far-field propagator. The measurement maps that exit wave to a measured pixel value, and the loss defines a loss function to attempt to minimize. The loss function we've chosen - the amplitude mean squared error - is the most broadly applicable one. - - -Device Management -+++++++++++++++++ - -Next we need to implement a :code:`to()` function, just like we did in the dataset, to allow the entire model to be moved between the GPU and CPU. - -.. code-block:: python - - def to(self, *args, **kwargs): - super(SimplePtycho, self).to(*args, **kwargs) - self.min_translation = self.min_translation.to(*args,**kwargs) - self.probe_basis = self.probe_basis.to(*args,**kwargs) - self.probe_norm = self.probe_norm.to(*args,**kwargs) - -We start by calling the same function for the superclass, which will take care of moving every parameter attached to the model. Then we manually take care of moving over the other variables which, while not being updated in the gradient descent, still need to be moved over to the new device! +The forward propagator maps the exit wave to the wave at the surface of the detector, here using a far-field propagator. The measurement maps that exit wave to a measured pixel value, and the loss defines a loss function to attempt to minimize. The loss function we've chosen - the amplitude mean squared error - is the most reliable one, and can also easily be overridden by an end user. Plotting @@ -447,62 +375,85 @@ The base CDIModel class has a function, :code:`model.inspect()`, which looks for .. code-block:: python + # This lists all the plots to display on a call to model.inspect() plot_list = [ ('Probe Amplitude', - lambda self, fig: tools.plotting.plot_amplitude(self.probe, fig=fig, basis=self.probe_basis)), + lambda self, fig: p.plot_amplitude(self.probe, fig=fig, basis=self.probe_basis)), ('Probe Phase', - lambda self, fig: tools.plotting.plot_phase(self.probe, fig=fig, basis=self.probe_basis)), + lambda self, fig: p.plot_phase(self.probe, fig=fig, basis=self.probe_basis)), ('Object Amplitude', - lambda self, fig: tools.plotting.plot_amplitude(self.obj, fig=fig, basis=self.probe_basis)), + lambda self, fig: p.plot_amplitude(self.obj, fig=fig, basis=self.probe_basis)), ('Object Phase', - lambda self, fig: tools.plotting.plot_phase(self.obj, fig=fig, basis=self.probe_basis)) + lambda self, fig: p.plot_phase(self.obj, fig=fig, basis=self.probe_basis)) ] - In this case, we've made use of the convenience plotting functions defined in :code:`tools.plotting`. Saving ++++++ -At the moment, there is no consistent way to save out the results across the board. However, a function :code:`save_results()` should be defined, which should save out the results of the reconstruction into some reasonably formatted python object. Here we return a dictionary with the probe and object: +By default, a function :code:`model.save_results()` is defined, which returns a python dictionary with an entry, :code:`'state_dict'`, containing all the registered parameters and buffers in the model. It also contains a basic record of the model's training history. This function is used internally by :code:`model.save_to_h5()`, as well as all other convenience functions for saving results. + +Sometimes, it is also useful to return a more user-friendly version of the results, such as a properly rescaled version of the probe. To make this possible, :code:`model.save_results()` is often overridden: + .. code-block:: python - def save_results(self): + def save_results(self, dataset): + # This will save out everything needed to recreate the object + # in the same state, but it's not the best formatted. + base_results = super().save_results() + + # So we also save out the main results in a more useable format + probe_basis = self.probe_basis.detach().cpu().numpy() probe = self.probe.detach().cpu().numpy() probe = probe * self.probe_norm.detach().cpu().numpy() obj = self.obj.detach().cpu().numpy() - return {'probe':probe,'obj':obj} + wavelength = self.wavelength.cpu().numpy() + results = { + 'probe_basis': probe_basis, + 'probe': probe, + 'obj': obj, + 'wavelength': wavelength, + } + return {**base_results, **results} + +However, it is perfectly possible to write a new ptychography model without overriding :code:`model.save_results()` + + Testing +++++++ -We can test this model with a simple script, shown below. By filling in the backend here, we've been able to create a ptychography model that can be accessed and used in reconstructions via the same interface as the models we discussed in the examples section. +We can test this model with a simple script, in examples/tutorial_finale.py. By filling in the backend here, we've been able to create a ptychography model that can be accessed and used in reconstructions via the same interface as the models we discussed in the examples section. .. code-block:: python - from basic_ptycho_dataset import BasicPtychoDataset + from tutorial_basic_ptycho_dataset import BasicPtychoDataset + from tutorial_simple_ptycho import SimplePtycho from h5py import File from matplotlib import pyplot as plt filename = 'example_data/lab_ptycho_data.cxi' with File(filename, 'r') as f: - dataset = BasicPtychoDataset.from_cxi(f) + dataset = BasicPtychoDataset.from_cxi(f) + + dataset.inspect() - model = SimplePtycho.from_dataset(dataset) - model.to(device='cuda') - dataset.get_as(device='cuda') - - for loss in model.Adam_optimize(100, dataset): - model.inspect(dataset) - print(model.report()) + model.to(device='mps')#cuda') + dataset.get_as(device='mps')#cuda') + for loss in model.Adam_optimize(10, dataset): + model.inspect(dataset) + print(model.report()) + + model.inspect(dataset) model.compare(dataset) plt.show() - + Happy modeling! diff --git a/examples/basic_ptycho_dataset.py b/examples/tutorial_basic_ptycho_dataset.py similarity index 88% rename from examples/basic_ptycho_dataset.py rename to examples/tutorial_basic_ptycho_dataset.py index 505a0b0..f68dea2 100644 --- a/examples/basic_ptycho_dataset.py +++ b/examples/tutorial_basic_ptycho_dataset.py @@ -1,4 +1,3 @@ -import numpy as np import torch as t from matplotlib import pyplot as plt from cdtools.datasets import CDataset @@ -14,7 +13,7 @@ class BasicPtychoDataset(CDataset): def __init__(self, translations, patterns, *args, **kwargs): """Initialize the dataset from python objects""" - super(BasicPtychoDataset,self).__init__(*args, **kwargs) + super().__init__(*args, **kwargs) self.translations = t.Tensor(translations).clone() self.patterns = t.Tensor(patterns).clone() @@ -27,7 +26,7 @@ class BasicPtychoDataset(CDataset): def to(self, *args, **kwargs): """Sends the relevant data to the given device and dtype""" - super(BasicPtychoDataset,self).to(*args,**kwargs) + super().to(*args,**kwargs) self.translations = self.translations.to(*args, **kwargs) self.patterns = self.patterns.to(*args, **kwargs) @@ -55,7 +54,7 @@ class BasicPtychoDataset(CDataset): def to_cxi(self, cxi_file): """Saves out a BasicPtychoDataset as a .cxi file""" - super(BasicPtychoDataset,self).to_cxi(cxi_file) + super().to_cxi(cxi_file) cdtdata.add_data(cxi_file, self.patterns, axes=self.axes) cdtdata.add_ptycho_translations(cxi_file, self.translations) @@ -63,6 +62,6 @@ class BasicPtychoDataset(CDataset): def inspect(self): """Plots a random diffraction pattern""" - index = np.random.randint(len(self)) + index = t.randint(len(self), (1,))[0] plt.figure() plt.imshow(self.patterns[index,:,:].cpu().numpy()) diff --git a/examples/tutorial_finale.py b/examples/tutorial_finale.py new file mode 100644 index 0000000..9f698b7 --- /dev/null +++ b/examples/tutorial_finale.py @@ -0,0 +1,23 @@ +from tutorial_basic_ptycho_dataset import BasicPtychoDataset +from tutorial_simple_ptycho import SimplePtycho +from h5py import File +from matplotlib import pyplot as plt + +filename = 'example_data/lab_ptycho_data.cxi' +with File(filename, 'r') as f: + dataset = BasicPtychoDataset.from_cxi(f) + +dataset.inspect() + +model = SimplePtycho.from_dataset(dataset) + +model.to(device='cuda') +dataset.get_as(device='cuda') + +for loss in model.Adam_optimize(10, dataset): + model.inspect(dataset) + print(model.report()) + +model.inspect(dataset) +model.compare(dataset) +plt.show() diff --git a/examples/tutorial_simple_ptycho.py b/examples/tutorial_simple_ptycho.py new file mode 100644 index 0000000..7e8a3e5 --- /dev/null +++ b/examples/tutorial_simple_ptycho.py @@ -0,0 +1,140 @@ +import torch as t +from cdtools.models import CDIModel +from cdtools import tools +from cdtools.tools import plotting as p + +__all__ = ['SimplePtycho'] + +class SimplePtycho(CDIModel): + """A simple ptychography model to demonstrate the structure of a model + """ + def __init__( + self, + wavelength, + probe_basis, + probe_guess, + obj_guess, + min_translation = [0,0], + ): + + # We initialize the superclass + super().__init__() + + # We register all the constants, like wavelength, as buffers. This + # lets the model hook into some nice pytorch features, like using + # model.to, and broadcasting the model state across multiple GPUs + self.register_buffer('wavelength', t.as_tensor(wavelength)) + self.register_buffer('min_translation', t.as_tensor(min_translation)) + self.register_buffer('probe_basis', t.as_tensor(probe_basis)) + + # We cast the probe and object to 64-bit complex tensors + probe_guess = t.as_tensor(probe_guess, dtype=t.complex64) + obj_guess = t.as_tensor(obj_guess, dtype=t.complex64) + + # We rescale the probe here so it learns at the same rate as the + # object when using optimizers, like Adam, which set the stepsize + # to a fixed maximum + self.register_buffer('probe_norm', t.max(t.abs(probe_guess))) + + # And we store the probe and object guesses as parameters, so + # they can get optimized by pytorch + self.probe = t.nn.Parameter(probe_guess / self.probe_norm) + self.obj = t.nn.Parameter(obj_guess) + + + @classmethod + def from_dataset(cls, dataset): + + # We get the key geometry information from the dataset + wavelength = dataset.wavelength + det_basis = dataset.detector_geometry['basis'] + det_shape = dataset[0][1].shape + distance = dataset.detector_geometry['distance'] + + # Then, we generate the probe geometry + ewg = tools.initializers.exit_wave_geometry + probe_basis = ewg(det_basis, det_shape, wavelength, distance) + + # Next generate the object geometry from the probe geometry and + # the translations + (indices, translations), patterns = dataset[:] + pix_translations = tools.interactions.translations_to_pixel( + probe_basis, + translations, + ) + obj_size, min_translation = tools.initializers.calc_object_setup( + det_shape, + pix_translations, + ) + + # Finally, initialize the probe and object using this information + probe = tools.initializers.SHARP_style_probe(dataset) + obj = t.ones(obj_size).to(dtype=t.complex64) + + return cls( + wavelength, + probe_basis, + probe, + obj, + min_translation=min_translation + ) + + + def interaction(self, index, translations): + + # We map from real-space to pixel-space units + pix_trans = tools.interactions.translations_to_pixel( + self.probe_basis, + translations) + pix_trans -= self.min_translation + + # This function extracts the appropriate window from the object and + # multiplies the object and probe functions + return tools.interactions.ptycho_2D_round( + self.probe_norm * self.probe, + self.obj, + pix_trans) + + + def forward_propagator(self, wavefields): + return tools.propagators.far_field(wavefields) + + def measurement(self, wavefields): + return tools.measurements.intensity(wavefields) + + def loss(self, real_data, sim_data): + return tools.losses.amplitude_mse(real_data, sim_data) + + + # This lists all the plots to display on a call to model.inspect() + plot_list = [ + ('Probe Amplitude', + lambda self, fig: p.plot_amplitude(self.probe, fig=fig, basis=self.probe_basis)), + ('Probe Phase', + lambda self, fig: p.plot_phase(self.probe, fig=fig, basis=self.probe_basis)), + ('Object Amplitude', + lambda self, fig: p.plot_amplitude(self.obj, fig=fig, basis=self.probe_basis)), + ('Object Phase', + lambda self, fig: p.plot_phase(self.obj, fig=fig, basis=self.probe_basis)) + ] + + def save_results(self, dataset): + # This will save out everything needed to recreate the object + # in the same state, but it's not the best formatted. + base_results = super().save_results() + + # So we also save out the main results in a more useable format + probe_basis = self.probe_basis.detach().cpu().numpy() + probe = self.probe.detach().cpu().numpy() + probe = probe * self.probe_norm.detach().cpu().numpy() + obj = self.obj.detach().cpu().numpy() + wavelength = self.wavelength.cpu().numpy() + + results = { + 'probe_basis': probe_basis, + 'probe': probe, + 'obj': obj, + 'wavelength': wavelength, + } + + return {**base_results, **results} diff --git a/src/cdtools/models/simple_ptycho.py b/src/cdtools/models/simple_ptycho.py index 13dde61..5435c66 100644 --- a/src/cdtools/models/simple_ptycho.py +++ b/src/cdtools/models/simple_ptycho.py @@ -1,23 +1,16 @@ import torch as t from cdtools.models import CDIModel -from cdtools.datasets import Ptycho2DDataset from cdtools import tools from cdtools.tools import plotting as p -from copy import copy -from torch.utils import data as torchdata -from datetime import datetime -import numpy as np __all__ = ['SimplePtycho'] - class SimplePtycho(CDIModel): - """A simple ptychography model for exploring ideas and extensions + """A simple ptychography model to demonstrate the structure of a model """ def __init__( self, wavelength, - detector_geometry, probe_basis, probe_guess, obj_guess, @@ -25,23 +18,22 @@ class SimplePtycho(CDIModel): ): # We initialize the superclass - super(SimplePtycho,self).__init__() + super().__init__() - # We register all the constants, like wavelength, as buffers. - # This lets the model hook into some nice pytorch features, like - # using model.to, and in principle should make easier to broadcast - # across multiple GPUs + # We register all the constants, like wavelength, as buffers. This + # lets the model hook into some nice pytorch features, like using + # model.to, and broadcasting the model state across multiple GPUs self.register_buffer('wavelength', t.as_tensor(wavelength)) - self.store_detector_geometry(detector_geometry) - self.register_buffer('min_translation', t.as_tensor(min_translation)) self.register_buffer('probe_basis', t.as_tensor(probe_basis)) + # We cast the probe and object to 64-bit complex tensors probe_guess = t.as_tensor(probe_guess, dtype=t.complex64) obj_guess = t.as_tensor(obj_guess, dtype=t.complex64) # We rescale the probe here so it learns at the same rate as the - # object + # object when using optimizers, like Adam, which set the stepsize + # to a fixed maximum self.register_buffer('probe_norm', t.max(t.abs(probe_guess))) # And we store the probe and object guesses as parameters, so @@ -59,15 +51,13 @@ class SimplePtycho(CDIModel): det_shape = dataset[0][1].shape distance = dataset.detector_geometry['distance'] - # We extract all the diffraction patterns and translations - (indices, translations), patterns = dataset[:] - # Then, we generate the probe geometry ewg = tools.initializers.exit_wave_geometry probe_basis = ewg(det_basis, det_shape, wavelength, distance) # Next generate the object geometry from the probe geometry and # the translations + (indices, translations), patterns = dataset[:] pix_translations = tools.interactions.translations_to_pixel( probe_basis, translations, @@ -83,7 +73,6 @@ class SimplePtycho(CDIModel): return cls( wavelength, - dataset.detector_geometry, probe_basis, probe, obj, @@ -98,10 +87,9 @@ class SimplePtycho(CDIModel): self.probe_basis, translations) pix_trans -= self.min_translation - - # This function gets the proper, pixel-accurate crops of the - # object array, and uses a sinc-interpolated subpixel shift of - # the probe to reach subpixel accuracy + + # This function extracts the appropriate window from the object and + # multiplies the object and probe functions return tools.interactions.ptycho_2D_round( self.probe_norm * self.probe, self.obj, @@ -111,15 +99,9 @@ class SimplePtycho(CDIModel): def forward_propagator(self, wavefields): return tools.propagators.far_field(wavefields) - - def backward_propagator(self, wavefields): - return tools.propagators.inverse_far_field(wavefields) - - def measurement(self, wavefields): return tools.measurements.intensity(wavefields) - def loss(self, real_data, sim_data): return tools.losses.amplitude_mse(real_data, sim_data) @@ -136,3 +118,23 @@ class SimplePtycho(CDIModel): lambda self, fig: p.plot_phase(self.obj, fig=fig, basis=self.probe_basis)) ] + def save_results(self, dataset): + # This will save out everything needed to recreate the object + # in the same state, but it's not the best formatted. + base_results = super().save_results() + + # So we also save out the main results in a more useable format + probe_basis = self.probe_basis.detach().cpu().numpy() + probe = self.probe.detach().cpu().numpy() + probe = probe * self.probe_norm.detach().cpu().numpy() + obj = self.obj.detach().cpu().numpy() + wavelength = self.wavelength.cpu().numpy() + + results = { + 'probe_basis': probe_basis, + 'probe': probe, + 'obj': obj, + 'wavelength': wavelength, + } + + return {**base_results, **results} diff --git a/src/cdtools/tools/__init__.py b/src/cdtools/tools/__init__.py index ade4558..6adb554 100644 --- a/src/cdtools/tools/__init__.py +++ b/src/cdtools/tools/__init__.py @@ -23,4 +23,4 @@ from cdtools.tools import interactions from cdtools.tools import propagators from cdtools.tools import measurements from cdtools.tools import analysis -from cdtools.tools import atoms + diff --git a/src/cdtools/tools/analysis/__init__.py b/src/cdtools/tools/analysis/__init__.py index b44acc1..7939bf1 100644 --- a/src/cdtools/tools/analysis/__init__.py +++ b/src/cdtools/tools/analysis/__init__.py @@ -1 +1,2 @@ from cdtools.tools.analysis.analysis import * +from cdtools.tools.analysis.analysis import __all__, __doc__ diff --git a/src/cdtools/tools/atoms/__init__.py b/src/cdtools/tools/atoms/__init__.py deleted file mode 100644 index 6f5766b..0000000 --- a/src/cdtools/tools/atoms/__init__.py +++ /dev/null @@ -1 +0,0 @@ -from cdtools.tools.atoms.atoms import * diff --git a/src/cdtools/tools/atoms/atoms.py b/src/cdtools/tools/atoms/atoms.py deleted file mode 100644 index d9633cd..0000000 --- a/src/cdtools/tools/atoms/atoms.py +++ /dev/null @@ -1,1291 +0,0 @@ -"""Contains functions to generate standard object functions for atoms - -The atomic scattering factors used to derive these object functions are -pulled from E.J Kirkland, Advanced Computing in Electron Microscopy, -Appendix C. doi: 10.1007/978-1-4419-6533-2_11 - -They are actually taken from https://github.com/LeBeauGroup/pyMultislicer -written by Jim LeBeau, but above is the original reference. -""" - -import numpy as np -import torch as t - - -__all__ = ['generate_k_grid','generate_atom'] - - -def fParams(Z): - # This function ruthlessly plagiarized from pyMultislicer - fparams = {z: [0 for _ in range(0, 12)] for z in range(1, 104)} - fparams[1][0] = 4.20298324e-003 - fparams[1][1] = 2.25350888e-001 - fparams[1][2] = 6.27762505e-002 - fparams[1][3] = 2.25366950e-001 - fparams[1][4] = 3.00907347e-002 - fparams[1][5] = 2.25331756e-001 - fparams[1][6] = 6.77756695e-002 - fparams[1][7] = 4.38854001e+000 - fparams[1][8] = 3.56609237e-003 - fparams[1][9] = 4.03884823e-001 - fparams[1][10] = 2.76135815e-002 - fparams[1][11] = 1.44490166e+000 - fparams[2][0] = 1.87543704e-005 - fparams[2][1] = 2.12427997e-001 - fparams[2][2] = 4.10595800e-004 - fparams[2][3] = 3.32212279e-001 - fparams[2][4] = 1.96300059e-001 - fparams[2][5] = 5.17325152e-001 - fparams[2][6] = 8.36015738e-003 - fparams[2][7] = 3.66668239e-001 - fparams[2][8] = 2.95102022e-002 - fparams[2][9] = 1.37171827e+000 - fparams[2][10] = 4.65928982e-007 - fparams[2][11] = 3.75768025e+004 - fparams[3][0] = 7.45843816e-002 - fparams[3][1] = 8.81151424e-001 - fparams[3][2] = 7.15382250e-002 - fparams[3][3] = 4.59142904e-002 - fparams[3][4] = 1.45315229e-001 - fparams[3][5] = 8.81301714e-001 - fparams[3][6] = 1.12125769e+000 - fparams[3][7] = 1.88483665e+001 - fparams[3][8] = 2.51736525e-003 - fparams[3][9] = 1.59189995e-001 - fparams[3][10] = 3.58434971e-001 - fparams[3][11] = 6.12371000e+000 - fparams[4][0] = 6.11642897e-002 - fparams[4][1] = 9.90182132e-002 - fparams[4][2] = 1.25755034e-001 - fparams[4][3] = 9.90272412e-002 - fparams[4][4] = 2.00831548e-001 - fparams[4][5] = 1.87392509e+000 - fparams[4][6] = 7.87242876e-001 - fparams[4][7] = 9.32794929e+000 - fparams[4][8] = 1.58847850e-003 - fparams[4][9] = 8.91900236e-002 - fparams[4][10] = 2.73962031e-001 - fparams[4][11] = 3.20687658e+000 - fparams[5][0] = 1.25716066e-001 - fparams[5][1] = 1.48258830e-001 - fparams[5][2] = 1.73314452e-001 - fparams[5][3] = 1.48257216e-001 - fparams[5][4] = 1.84774811e-001 - fparams[5][5] = 3.34227311e+000 - fparams[5][6] = 1.95250221e-001 - fparams[5][7] = 1.97339463e+000 - fparams[5][8] = 5.29642075e-001 - fparams[5][9] = 5.70035553e+000 - fparams[5][10] = 1.08230500e-003 - fparams[5][11] = 5.64857237e-002 - fparams[6][0] = 2.12080767e-001 - fparams[6][1] = 2.08605417e-001 - fparams[6][2] = 1.99811865e-001 - fparams[6][3] = 2.08610186e-001 - fparams[6][4] = 1.68254385e-001 - fparams[6][5] = 5.57870773e+000 - fparams[6][6] = 1.42048360e-001 - fparams[6][7] = 1.33311887e+000 - fparams[6][8] = 3.63830672e-001 - fparams[6][9] = 3.80800263e+000 - fparams[6][10] = 8.35012044e-004 - fparams[6][11] = 4.03982620e-002 - fparams[7][0] = 5.33015554e-001 - fparams[7][1] = 2.90952515e-001 - fparams[7][2] = 5.29008883e-002 - fparams[7][3] = 1.03547896e+001 - fparams[7][4] = 9.24159648e-002 - fparams[7][5] = 1.03540028e+001 - fparams[7][6] = 2.61799101e-001 - fparams[7][7] = 2.76252723e+000 - fparams[7][8] = 8.80262108e-004 - fparams[7][9] = 3.47681236e-002 - fparams[7][10] = 1.10166555e-001 - fparams[7][11] = 9.93421736e-001 - fparams[8][0] = 3.39969204e-001 - fparams[8][1] = 3.81570280e-001 - fparams[8][2] = 3.07570172e-001 - fparams[8][3] = 3.81571436e-001 - fparams[8][4] = 1.30369072e-001 - fparams[8][5] = 1.91919745e+001 - fparams[8][6] = 8.83326058e-002 - fparams[8][7] = 7.60635525e-001 - fparams[8][8] = 1.96586700e-001 - fparams[8][9] = 2.07401094e+000 - fparams[8][10] = 9.96220028e-004 - fparams[8][11] = 3.03266869e-002 - fparams[9][0] = 2.30560593e-001 - fparams[9][1] = 4.80754213e-001 - fparams[9][2] = 5.26889648e-001 - fparams[9][3] = 4.80763895e-001 - fparams[9][4] = 1.24346755e-001 - fparams[9][5] = 3.95306720e+001 - fparams[9][6] = 1.24616894e-003 - fparams[9][7] = 2.62181803e-002 - fparams[9][8] = 7.20452555e-002 - fparams[9][9] = 5.92495593e-001 - fparams[9][10] = 1.53075777e-001 - fparams[9][11] = 1.59127671e+000 - fparams[10][0] = 4.08371771e-001 - fparams[10][1] = 5.88228627e-001 - fparams[10][2] = 4.54418858e-001 - fparams[10][3] = 5.88288655e-001 - fparams[10][4] = 1.44564923e-001 - fparams[10][5] = 1.21246013e+002 - fparams[10][6] = 5.91531395e-002 - fparams[10][7] = 4.63963540e-001 - fparams[10][8] = 1.24003718e-001 - fparams[10][9] = 1.23413025e+000 - fparams[10][10] = 1.64986037e-003 - fparams[10][11] = 2.05869217e-002 - fparams[11][0] = 1.36471662e-001 - fparams[11][1] = 4.99965301e-002 - fparams[11][2] = 7.70677865e-001 - fparams[11][3] = 8.81899664e-001 - fparams[11][4] = 1.56862014e-001 - fparams[11][5] = 1.61768579e+001 - fparams[11][6] = 9.96821513e-001 - fparams[11][7] = 2.00132610e+001 - fparams[11][8] = 3.80304670e-002 - fparams[11][9] = 2.60516254e-001 - fparams[11][10] = 1.27685089e-001 - fparams[11][11] = 6.99559329e-001 - fparams[12][0] = 3.04384121e-001 - fparams[12][1] = 8.42014377e-002 - fparams[12][2] = 7.56270563e-001 - fparams[12][3] = 1.64065598e+000 - fparams[12][4] = 1.01164809e-001 - fparams[12][5] = 2.97142975e+001 - fparams[12][6] = 3.45203403e-002 - fparams[12][7] = 2.16596094e-001 - fparams[12][8] = 9.71751327e-001 - fparams[12][9] = 1.21236852e+001 - fparams[12][10] = 1.20593012e-001 - fparams[12][11] = 5.60865838e-001 - fparams[13][0] = 7.77419424e-001 - fparams[13][1] = 2.71058227e+000 - fparams[13][2] = 5.78312036e-002 - fparams[13][3] = 7.17532098e+001 - fparams[13][4] = 4.26386499e-001 - fparams[13][5] = 9.13331555e-002 - fparams[13][6] = 1.13407220e-001 - fparams[13][7] = 4.48867451e-001 - fparams[13][8] = 7.90114035e-001 - fparams[13][9] = 8.66366718e+000 - fparams[13][10] = 3.23293496e-002 - fparams[13][11] = 1.78503463e-001 - fparams[14][0] = 1.06543892e+000 - fparams[14][1] = 1.04118455e+000 - fparams[14][2] = 1.20143691e-001 - fparams[14][3] = 6.87113368e+001 - fparams[14][4] = 1.80915263e-001 - fparams[14][5] = 8.87533926e-002 - fparams[14][6] = 1.12065620e+000 - fparams[14][7] = 3.70062619e+000 - fparams[14][8] = 3.05452816e-002 - fparams[14][9] = 2.14097897e-001 - fparams[14][10] = 1.59963502e+000 - fparams[14][11] = 9.99096638e+000 - fparams[15][0] = 1.05284447e+000 - fparams[15][1] = 1.31962590e+000 - fparams[15][2] = 2.99440284e-001 - fparams[15][3] = 1.28460520e-001 - fparams[15][4] = 1.17460748e-001 - fparams[15][5] = 1.02190163e+002 - fparams[15][6] = 9.60643452e-001 - fparams[15][7] = 2.87477555e+000 - fparams[15][8] = 2.63555748e-002 - fparams[15][9] = 1.82076844e-001 - fparams[15][10] = 1.38059330e+000 - fparams[15][11] = 7.49165526e+000 - fparams[16][0] = 1.01646916e+000 - fparams[16][1] = 1.69181965e+000 - fparams[16][2] = 4.41766748e-001 - fparams[16][3] = 1.74180288e-001 - fparams[16][4] = 1.21503863e-001 - fparams[16][5] = 1.67011091e+002 - fparams[16][6] = 8.27966670e-001 - fparams[16][7] = 2.30342810e+000 - fparams[16][8] = 2.33022533e-002 - fparams[16][9] = 1.56954150e-001 - fparams[16][10] = 1.18302846e+000 - fparams[16][11] = 5.85782891e+000 - fparams[17][0] = 9.44221116e-001 - fparams[17][1] = 2.40052374e-001 - fparams[17][2] = 4.37322049e-001 - fparams[17][3] = 9.30510439e+000 - fparams[17][4] = 2.54547926e-001 - fparams[17][5] = 9.30486346e+000 - fparams[17][6] = 5.47763323e-002 - fparams[17][7] = 1.68655688e-001 - fparams[17][8] = 8.00087488e-001 - fparams[17][9] = 2.97849774e+000 - fparams[17][10] = 1.07488641e-002 - fparams[17][11] = 6.84240646e-002 - fparams[18][0] = 1.06983288e+000 - fparams[18][1] = 2.87791022e-001 - fparams[18][2] = 4.24631786e-001 - fparams[18][3] = 1.24156957e+001 - fparams[18][4] = 2.43897949e-001 - fparams[18][5] = 1.24158868e+001 - fparams[18][6] = 4.79446296e-002 - fparams[18][7] = 1.36979796e-001 - fparams[18][8] = 7.64958952e-001 - fparams[18][9] = 2.43940729e+000 - fparams[18][10] = 8.23128431e-003 - fparams[18][11] = 5.27258749e-002 - fparams[19][0] = 6.92717865e-001 - fparams[19][1] = 7.10849990e+000 - fparams[19][2] = 9.65161085e-001 - fparams[19][3] = 3.57532901e-001 - fparams[19][4] = 1.48466588e-001 - fparams[19][5] = 3.93763275e-002 - fparams[19][6] = 2.64645027e-002 - fparams[19][7] = 1.03591321e-001 - fparams[19][8] = 1.80883768e+000 - fparams[19][9] = 3.22845199e+001 - fparams[19][10] = 5.43900018e-001 - fparams[19][11] = 1.67791374e+000 - fparams[20][0] = 3.66902871e-001 - fparams[20][1] = 6.14274129e-002 - fparams[20][2] = 8.66378999e-001 - fparams[20][3] = 5.70881727e-001 - fparams[20][4] = 6.67203300e-001 - fparams[20][5] = 7.82965639e+000 - fparams[20][6] = 4.87743636e-001 - fparams[20][7] = 1.32531318e+000 - fparams[20][8] = 1.82406314e+000 - fparams[20][9] = 2.10056032e+001 - fparams[20][10] = 2.20248453e-002 - fparams[20][11] = 9.11853450e-002 - fparams[21][0] = 3.78871777e-001 - fparams[21][1] = 6.98910162e-002 - fparams[21][2] = 9.00022505e-001 - fparams[21][3] = 5.21061541e-001 - fparams[21][4] = 7.15288914e-001 - fparams[21][5] = 7.87707920e+000 - fparams[21][6] = 1.88640973e-002 - fparams[21][7] = 8.17512708e-002 - fparams[21][8] = 4.07945949e-001 - fparams[21][9] = 1.11141388e+000 - fparams[21][10] = 1.61786540e+000 - fparams[21][11] = 1.80840759e+001 - fparams[22][0] = 3.62383267e-001 - fparams[22][1] = 7.54707114e-002 - fparams[22][2] = 9.84232966e-001 - fparams[22][3] = 4.97757309e-001 - fparams[22][4] = 7.41715642e-001 - fparams[22][5] = 8.17659391e+000 - fparams[22][6] = 3.62555269e-001 - fparams[22][7] = 9.55524906e-001 - fparams[22][8] = 1.49159390e+000 - fparams[22][9] = 1.62221677e+001 - fparams[22][10] = 1.61659509e-002 - fparams[22][11] = 7.33140839e-002 - fparams[23][0] = 3.52961378e-001 - fparams[23][1] = 8.19204103e-002 - fparams[23][2] = 7.46791014e-001 - fparams[23][3] = 8.81189511e+000 - fparams[23][4] = 1.08364068e+000 - fparams[23][5] = 5.10646075e-001 - fparams[23][6] = 1.39013610e+000 - fparams[23][7] = 1.48901841e+001 - fparams[23][8] = 3.31273356e-001 - fparams[23][9] = 8.38543079e-001 - fparams[23][10] = 1.40422612e-002 - fparams[23][11] = 6.57432678e-002 - fparams[24][0] = 1.34348379e+000 - fparams[24][1] = 1.25814353e+000 - fparams[24][2] = 5.07040328e-001 - fparams[24][3] = 1.15042811e+001 - fparams[24][4] = 4.26358955e-001 - fparams[24][5] = 8.53660389e-002 - fparams[24][6] = 1.17241826e-002 - fparams[24][7] = 6.00177061e-002 - fparams[24][8] = 5.11966516e-001 - fparams[24][9] = 1.53772451e+000 - fparams[24][10] = 3.38285828e-001 - fparams[24][11] = 6.62418319e-001 - fparams[25][0] = 3.26697613e-001 - fparams[25][1] = 8.88813083e-002 - fparams[25][2] = 7.17297000e-001 - fparams[25][3] = 1.11300198e+001 - fparams[25][4] = 1.33212464e+000 - fparams[25][5] = 5.82141104e-001 - fparams[25][6] = 2.80801702e-001 - fparams[25][7] = 6.71583145e-001 - fparams[25][8] = 1.15499241e+000 - fparams[25][9] = 1.26825395e+001 - fparams[25][10] = 1.11984488e-002 - fparams[25][11] = 5.32334467e-002 - fparams[26][0] = 3.13454847e-001 - fparams[26][1] = 8.99325756e-002 - fparams[26][2] = 6.89290016e-001 - fparams[26][3] = 1.30366038e+001 - fparams[26][4] = 1.47141531e+000 - fparams[26][5] = 6.33345291e-001 - fparams[26][6] = 1.03298688e+000 - fparams[26][7] = 1.16783425e+001 - fparams[26][8] = 2.58280285e-001 - fparams[26][9] = 6.09116446e-001 - fparams[26][10] = 1.03460690e-002 - fparams[26][11] = 4.81610627e-002 - fparams[27][0] = 3.15878278e-001 - fparams[27][1] = 9.46683246e-002 - fparams[27][2] = 1.60139005e+000 - fparams[27][3] = 6.99436449e-001 - fparams[27][4] = 6.56394338e-001 - fparams[27][5] = 1.56954403e+001 - fparams[27][6] = 9.36746624e-001 - fparams[27][7] = 1.09392410e+001 - fparams[27][8] = 9.77562646e-003 - fparams[27][9] = 4.37446816e-002 - fparams[27][10] = 2.38378578e-001 - fparams[27][11] = 5.56286483e-001 - fparams[28][0] = 1.72254630e+000 - fparams[28][1] = 7.76606908e-001 - fparams[28][2] = 3.29543044e-001 - fparams[28][3] = 1.02262360e-001 - fparams[28][4] = 6.23007200e-001 - fparams[28][5] = 1.94156207e+001 - fparams[28][6] = 9.43496513e-003 - fparams[28][7] = 3.98684596e-002 - fparams[28][8] = 8.54063515e-001 - fparams[28][9] = 1.04078166e+001 - fparams[28][10] = 2.21073515e-001 - fparams[28][11] = 5.10869330e-001 - fparams[29][0] = 3.58774531e-001 - fparams[29][1] = 1.06153463e-001 - fparams[29][2] = 1.76181348e+000 - fparams[29][3] = 1.01640995e+000 - fparams[29][4] = 6.36905053e-001 - fparams[29][5] = 1.53659093e+001 - fparams[29][6] = 7.44930667e-003 - fparams[29][7] = 3.85345989e-002 - fparams[29][8] = 1.89002347e-001 - fparams[29][9] = 3.98427790e-001 - fparams[29][10] = 2.29619589e-001 - fparams[29][11] = 9.01419843e-001 - fparams[30][0] = 5.70893973e-001 - fparams[30][1] = 1.26534614e-001 - fparams[30][2] = 1.98908856e+000 - fparams[30][3] = 2.17781965e+000 - fparams[30][4] = 3.06060585e-001 - fparams[30][5] = 3.78619003e+001 - fparams[30][6] = 2.35600223e-001 - fparams[30][7] = 3.67019041e-001 - fparams[30][8] = 3.97061102e-001 - fparams[30][9] = 8.66419596e-001 - fparams[30][10] = 6.85657228e-003 - fparams[30][11] = 3.35778823e-002 - fparams[31][0] = 6.25528464e-001 - fparams[31][1] = 1.10005650e-001 - fparams[31][2] = 2.05302901e+000 - fparams[31][3] = 2.41095786e+000 - fparams[31][4] = 2.89608120e-001 - fparams[31][5] = 4.78685736e+001 - fparams[31][6] = 2.07910594e-001 - fparams[31][7] = 3.27807224e-001 - fparams[31][8] = 3.45079617e-001 - fparams[31][9] = 7.43139061e-001 - fparams[31][10] = 6.55634298e-003 - fparams[31][11] = 3.09411369e-002 - fparams[32][0] = 5.90952690e-001 - fparams[32][1] = 1.18375976e-001 - fparams[32][2] = 5.39980660e-001 - fparams[32][3] = 7.18937433e+001 - fparams[32][4] = 2.00626188e+000 - fparams[32][5] = 1.39304889e+000 - fparams[32][6] = 7.49705041e-001 - fparams[32][7] = 6.89943350e+000 - fparams[32][8] = 1.83581347e-001 - fparams[32][9] = 3.64667232e-001 - fparams[32][10] = 9.52190743e-003 - fparams[32][11] = 2.69888650e-002 - fparams[33][0] = 7.77875218e-001 - fparams[33][1] = 1.50733157e-001 - fparams[33][2] = 5.93848150e-001 - fparams[33][3] = 1.42882209e+002 - fparams[33][4] = 1.95918751e+000 - fparams[33][5] = 1.74750339e+000 - fparams[33][6] = 1.79880226e-001 - fparams[33][7] = 3.31800852e-001 - fparams[33][8] = 8.63267222e-001 - fparams[33][9] = 5.85490274e+000 - fparams[33][10] = 9.59053427e-003 - fparams[33][11] = 2.33777569e-002 - fparams[34][0] = 9.58390681e-001 - fparams[34][1] = 1.83775557e-001 - fparams[34][2] = 6.03851342e-001 - fparams[34][3] = 1.96819224e+002 - fparams[34][4] = 1.90828931e+000 - fparams[34][5] = 2.15082053e+000 - fparams[34][6] = 1.73885956e-001 - fparams[34][7] = 3.00006024e-001 - fparams[34][8] = 9.35265145e-001 - fparams[34][9] = 4.92471215e+000 - fparams[34][10] = 8.62254658e-003 - fparams[34][11] = 2.12308108e-002 - fparams[35][0] = 1.14136170e+000 - fparams[35][1] = 2.18708710e-001 - fparams[35][2] = 5.18118737e-001 - fparams[35][3] = 1.93916682e+002 - fparams[35][4] = 1.85731975e+000 - fparams[35][5] = 2.65755396e+000 - fparams[35][6] = 1.68217399e-001 - fparams[35][7] = 2.71719918e-001 - fparams[35][8] = 9.75705606e-001 - fparams[35][9] = 4.19482500e+000 - fparams[35][10] = 7.24187871e-003 - fparams[35][11] = 1.99325718e-002 - fparams[36][0] = 3.24386970e-001 - fparams[36][1] = 6.31317973e+001 - fparams[36][2] = 1.31732163e+000 - fparams[36][3] = 2.54706036e-001 - fparams[36][4] = 1.79912614e+000 - fparams[36][5] = 3.23668394e+000 - fparams[36][6] = 4.29961425e-003 - fparams[36][7] = 1.98965610e-002 - fparams[36][8] = 1.00429433e+000 - fparams[36][9] = 3.61094513e+000 - fparams[36][10] = 1.62188197e-001 - fparams[36][11] = 2.45583672e-001 - fparams[37][0] = 2.90445351e-001 - fparams[37][1] = 3.68420227e-002 - fparams[37][2] = 2.44201329e+000 - fparams[37][3] = 1.16013332e+000 - fparams[37][4] = 7.69435449e-001 - fparams[37][5] = 1.69591472e+001 - fparams[37][6] = 1.58687000e+000 - fparams[37][7] = 2.53082574e+000 - fparams[37][8] = 2.81617593e-003 - fparams[37][9] = 1.88577417e-002 - fparams[37][10] = 1.28663830e-001 - fparams[37][11] = 2.10753969e-001 - fparams[38][0] = 1.37373086e-002 - fparams[38][1] = 1.87469061e-002 - fparams[38][2] = 1.97548672e+000 - fparams[38][3] = 6.36079230e+000 - fparams[38][4] = 1.59261029e+000 - fparams[38][5] = 2.21992482e-001 - fparams[38][6] = 1.73263882e-001 - fparams[38][7] = 2.01624958e-001 - fparams[38][8] = 4.66280378e+000 - fparams[38][9] = 2.53027803e+001 - fparams[38][10] = 1.61265063e-003 - fparams[38][11] = 1.53610568e-002 - fparams[39][0] = 6.75302747e-001 - fparams[39][1] = 6.54331847e-002 - fparams[39][2] = 4.70286720e-001 - fparams[39][3] = 1.06108709e+002 - fparams[39][4] = 2.63497677e+000 - fparams[39][5] = 2.06643540e+000 - fparams[39][6] = 1.09621746e-001 - fparams[39][7] = 1.93131925e-001 - fparams[39][8] = 9.60348773e-001 - fparams[39][9] = 1.63310938e+000 - fparams[39][10] = 5.28921555e-003 - fparams[39][11] = 1.66083821e-002 - fparams[40][0] = 2.64365505e+000 - fparams[40][1] = 2.20202699e+000 - fparams[40][2] = 5.54225147e-001 - fparams[40][3] = 1.78260107e+002 - fparams[40][4] = 7.61376625e-001 - fparams[40][5] = 7.67218745e-002 - fparams[40][6] = 6.02946891e-003 - fparams[40][7] = 1.55143296e-002 - fparams[40][8] = 9.91630530e-002 - fparams[40][9] = 1.76175995e-001 - fparams[40][10] = 9.56782020e-001 - fparams[40][11] = 1.54330682e+000 - fparams[41][0] = 6.59532875e-001 - fparams[41][1] = 8.66145490e-002 - fparams[41][2] = 1.84545854e+000 - fparams[41][3] = 5.94774398e+000 - fparams[41][4] = 1.25584405e+000 - fparams[41][5] = 6.40851475e-001 - fparams[41][6] = 1.22253422e-001 - fparams[41][7] = 1.66646050e-001 - fparams[41][8] = 7.06638328e-001 - fparams[41][9] = 1.62853268e+000 - fparams[41][10] = 2.62381591e-003 - fparams[41][11] = 8.26257859e-003 - fparams[42][0] = 6.10160120e-001 - fparams[42][1] = 9.11628054e-002 - fparams[42][2] = 1.26544000e+000 - fparams[42][3] = 5.06776025e-001 - fparams[42][4] = 1.97428762e+000 - fparams[42][5] = 5.89590381e+000 - fparams[42][6] = 6.48028962e-001 - fparams[42][7] = 1.46634108e+000 - fparams[42][8] = 2.60380817e-003 - fparams[42][9] = 7.84336311e-003 - fparams[42][10] = 1.13887493e-001 - fparams[42][11] = 1.55114340e-001 - fparams[43][0] = 8.55189183e-001 - fparams[43][1] = 1.02962151e-001 - fparams[43][2] = 1.66219641e+000 - fparams[43][3] = 7.64907000e+000 - fparams[43][4] = 1.45575475e+000 - fparams[43][5] = 1.01639987e+000 - fparams[43][6] = 1.05445664e-001 - fparams[43][7] = 1.42303338e-001 - fparams[43][8] = 7.71657112e-001 - fparams[43][9] = 1.34659349e+000 - fparams[43][10] = 2.20992635e-003 - fparams[43][11] = 7.90358976e-003 - fparams[44][0] = 4.70847093e-001 - fparams[44][1] = 9.33029874e-002 - fparams[44][2] = 1.58180781e+000 - fparams[44][3] = 4.52831347e-001 - fparams[44][4] = 2.02419818e+000 - fparams[44][5] = 7.11489023e+000 - fparams[44][6] = 1.97036257e-003 - fparams[44][7] = 7.56181595e-003 - fparams[44][8] = 6.26912639e-001 - fparams[44][9] = 1.25399858e+000 - fparams[44][10] = 1.02641320e-001 - fparams[44][11] = 1.33786087e-001 - fparams[45][0] = 4.20051553e-001 - fparams[45][1] = 9.38882628e-002 - fparams[45][2] = 1.76266507e+000 - fparams[45][3] = 4.64441687e-001 - fparams[45][4] = 2.02735641e+000 - fparams[45][5] = 8.19346046e+000 - fparams[45][6] = 1.45487176e-003 - fparams[45][7] = 7.82704517e-003 - fparams[45][8] = 6.22809600e-001 - fparams[45][9] = 1.17194153e+000 - fparams[45][10] = 9.91529915e-002 - fparams[45][11] = 1.24532839e-001 - fparams[46][0] = 2.10475155e+000 - fparams[46][1] = 8.68606470e+000 - fparams[46][2] = 2.03884487e+000 - fparams[46][3] = 3.78924449e-001 - fparams[46][4] = 1.82067264e-001 - fparams[46][5] = 1.42921634e-001 - fparams[46][6] = 9.52040948e-002 - fparams[46][7] = 1.17125900e-001 - fparams[46][8] = 5.91445248e-001 - fparams[46][9] = 1.07843808e+000 - fparams[46][10] = 1.13328676e-003 - fparams[46][11] = 7.80252092e-003 - fparams[47][0] = 2.07981390e+000 - fparams[47][1] = 9.92540297e+000 - fparams[47][2] = 4.43170726e-001 - fparams[47][3] = 1.04920104e-001 - fparams[47][4] = 1.96515215e+000 - fparams[47][5] = 6.40103839e-001 - fparams[47][6] = 5.96130591e-001 - fparams[47][7] = 8.89594790e-001 - fparams[47][8] = 4.78016333e-001 - fparams[47][9] = 1.98509407e+000 - fparams[47][10] = 9.46458470e-002 - fparams[47][11] = 1.12744464e-001 - fparams[48][0] = 1.63657549e+000 - fparams[48][1] = 1.24540381e+001 - fparams[48][2] = 2.17927989e+000 - fparams[48][3] = 1.45134660e+000 - fparams[48][4] = 7.71300690e-001 - fparams[48][5] = 1.26695757e-001 - fparams[48][6] = 6.64193880e-001 - fparams[48][7] = 7.77659202e-001 - fparams[48][8] = 7.64563285e-001 - fparams[48][9] = 1.66075210e+000 - fparams[48][10] = 8.61126689e-002 - fparams[48][11] = 1.05728357e-001 - fparams[49][0] = 2.24820632e+000 - fparams[49][1] = 1.51913507e+000 - fparams[49][2] = 1.64706864e+000 - fparams[49][3] = 1.30113424e+001 - fparams[49][4] = 7.88679265e-001 - fparams[49][5] = 1.06128184e-001 - fparams[49][6] = 8.12579069e-002 - fparams[49][7] = 9.94045620e-002 - fparams[49][8] = 6.68280346e-001 - fparams[49][9] = 1.49742063e+000 - fparams[49][10] = 6.38467475e-001 - fparams[49][11] = 7.18422635e-001 - fparams[50][0] = 2.16644620e+000 - fparams[50][1] = 1.13174909e+001 - fparams[50][2] = 6.88691021e-001 - fparams[50][3] = 1.10131285e-001 - fparams[50][4] = 1.92431751e+000 - fparams[50][5] = 6.74464853e-001 - fparams[50][6] = 5.65359888e-001 - fparams[50][7] = 7.33564610e-001 - fparams[50][8] = 9.18683861e-001 - fparams[50][9] = 1.02310312e+001 - fparams[50][10] = 7.80542213e-002 - fparams[50][11] = 9.31104308e-002 - fparams[51][0] = 1.73662114e+000 - fparams[51][1] = 8.84334719e-001 - fparams[51][2] = 9.99871380e-001 - fparams[51][3] = 1.38462121e-001 - fparams[51][4] = 2.13972409e+000 - fparams[51][5] = 1.19666432e+001 - fparams[51][6] = 5.60566526e-001 - fparams[51][7] = 6.72672880e-001 - fparams[51][8] = 9.93772747e-001 - fparams[51][9] = 8.72330411e+000 - fparams[51][10] = 7.37374982e-002 - fparams[51][11] = 8.78577715e-002 - fparams[52][0] = 2.09383882e+000 - fparams[52][1] = 1.26856869e+001 - fparams[52][2] = 1.56940519e+000 - fparams[52][3] = 1.21236537e+000 - fparams[52][4] = 1.30941993e+000 - fparams[52][5] = 1.66633292e-001 - fparams[52][6] = 6.98067804e-002 - fparams[52][7] = 8.30817576e-002 - fparams[52][8] = 1.04969537e+000 - fparams[52][9] = 7.43147857e+000 - fparams[52][10] = 5.55594354e-001 - fparams[52][11] = 6.17487676e-001 - fparams[53][0] = 1.60186925e+000 - fparams[53][1] = 1.95031538e-001 - fparams[53][2] = 1.98510264e+000 - fparams[53][3] = 1.36976183e+001 - fparams[53][4] = 1.48226200e+000 - fparams[53][5] = 1.80304795e+000 - fparams[53][6] = 5.53807199e-001 - fparams[53][7] = 5.67912340e-001 - fparams[53][8] = 1.11728722e+000 - fparams[53][9] = 6.40879878e+000 - fparams[53][10] = 6.60720847e-002 - fparams[53][11] = 7.86615429e-002 - fparams[54][0] = 1.60015487e+000 - fparams[54][1] = 2.92913354e+000 - fparams[54][2] = 1.71644581e+000 - fparams[54][3] = 1.55882990e+001 - fparams[54][4] = 1.84968351e+000 - fparams[54][5] = 2.22525983e-001 - fparams[54][6] = 6.23813648e-002 - fparams[54][7] = 7.45581223e-002 - fparams[54][8] = 1.21387555e+000 - fparams[54][9] = 5.56013271e+000 - fparams[54][10] = 5.54051946e-001 - fparams[54][11] = 5.21994521e-001 - fparams[55][0] = 2.95236854e+000 - fparams[55][1] = 6.01461952e+000 - fparams[55][2] = 4.28105721e-001 - fparams[55][3] = 4.64151246e+001 - fparams[55][4] = 1.89599233e+000 - fparams[55][5] = 1.80109756e-001 - fparams[55][6] = 5.48012938e-002 - fparams[55][7] = 7.12799633e-002 - fparams[55][8] = 4.70838600e+000 - fparams[55][9] = 4.56702799e+001 - fparams[55][10] = 5.90356719e-001 - fparams[55][11] = 4.70236310e-001 - fparams[56][0] = 3.19434243e+000 - fparams[56][1] = 9.27352241e+000 - fparams[56][2] = 1.98289586e+000 - fparams[56][3] = 2.28741632e-001 - fparams[56][4] = 1.55121052e-001 - fparams[56][5] = 3.82000231e-002 - fparams[56][6] = 6.73222354e-002 - fparams[56][7] = 7.30961745e-002 - fparams[56][8] = 4.48474211e+000 - fparams[56][9] = 2.95703565e+001 - fparams[56][10] = 5.42674414e-001 - fparams[56][11] = 4.08647015e-001 - fparams[57][0] = 2.05036425e+000 - fparams[57][1] = 2.20348417e-001 - fparams[57][2] = 1.42114311e-001 - fparams[57][3] = 3.96438056e-002 - fparams[57][4] = 3.23538151e+000 - fparams[57][5] = 9.56979169e+000 - fparams[57][6] = 6.34683429e-002 - fparams[57][7] = 6.92443091e-002 - fparams[57][8] = 3.97960586e+000 - fparams[57][9] = 2.53178406e+001 - fparams[57][10] = 5.20116711e-001 - fparams[57][11] = 3.83614098e-001 - fparams[58][0] = 3.22990759e+000 - fparams[58][1] = 9.94660135e+000 - fparams[58][2] = 1.57618307e-001 - fparams[58][3] = 4.15378676e-002 - fparams[58][4] = 2.13477838e+000 - fparams[58][5] = 2.40480572e-001 - fparams[58][6] = 5.01907609e-001 - fparams[58][7] = 3.66252019e-001 - fparams[58][8] = 3.80889010e+000 - fparams[58][9] = 2.43275968e+001 - fparams[58][10] = 5.96625028e-002 - fparams[58][11] = 6.59653503e-002 - fparams[59][0] = 1.58189324e-001 - fparams[59][1] = 3.91309056e-002 - fparams[59][2] = 3.18141995e+000 - fparams[59][3] = 1.04139545e+001 - fparams[59][4] = 2.27622140e+000 - fparams[59][5] = 2.81671757e-001 - fparams[59][6] = 3.97705472e+000 - fparams[59][7] = 2.61872978e+001 - fparams[59][8] = 5.58448277e-002 - fparams[59][9] = 6.30921695e-002 - fparams[59][10] = 4.85207954e-001 - fparams[59][11] = 3.54234369e-001 - fparams[60][0] = 1.81379417e-001 - fparams[60][1] = 4.37324793e-002 - fparams[60][2] = 3.17616396e+000 - fparams[60][3] = 1.07842572e+001 - fparams[60][4] = 2.35221519e+000 - fparams[60][5] = 3.05571833e-001 - fparams[60][6] = 3.83125763e+000 - fparams[60][7] = 2.54745408e+001 - fparams[60][8] = 5.25889976e-002 - fparams[60][9] = 6.02676073e-002 - fparams[60][10] = 4.70090742e-001 - fparams[60][11] = 3.39017003e-001 - fparams[61][0] = 1.92986811e-001 - fparams[61][1] = 4.37785970e-002 - fparams[61][2] = 2.43756023e+000 - fparams[61][3] = 3.29336996e-001 - fparams[61][4] = 3.17248504e+000 - fparams[61][5] = 1.11259996e+001 - fparams[61][6] = 3.58105414e+000 - fparams[61][7] = 2.46709586e+001 - fparams[61][8] = 4.56529394e-001 - fparams[61][9] = 3.24990282e-001 - fparams[61][10] = 4.94812177e-002 - fparams[61][11] = 5.76553100e-002 - fparams[62][0] = 2.12002595e-001 - fparams[62][1] = 4.57703608e-002 - fparams[62][2] = 3.16891754e+000 - fparams[62][3] = 1.14536599e+001 - fparams[62][4] = 2.51503494e+000 - fparams[62][5] = 3.55561054e-001 - fparams[62][6] = 4.44080845e-001 - fparams[62][7] = 3.11953363e-001 - fparams[62][8] = 3.36742101e+000 - fparams[62][9] = 2.40291435e+001 - fparams[62][10] = 4.65652543e-002 - fparams[62][11] = 5.52266819e-002 - fparams[63][0] = 2.59355002e+000 - fparams[63][1] = 3.82452612e-001 - fparams[63][2] = 3.16557522e+000 - fparams[63][3] = 1.17675155e+001 - fparams[63][4] = 2.29402652e-001 - fparams[63][5] = 4.76642249e-002 - fparams[63][6] = 4.32257780e-001 - fparams[63][7] = 2.99719833e-001 - fparams[63][8] = 3.17261920e+000 - fparams[63][9] = 2.34462738e+001 - fparams[63][10] = 4.37958317e-002 - fparams[63][11] = 5.29440680e-002 - fparams[64][0] = 3.19144939e+000 - fparams[64][1] = 1.20224655e+001 - fparams[64][2] = 2.55766431e+000 - fparams[64][3] = 4.08338876e-001 - fparams[64][4] = 3.32681934e-001 - fparams[64][5] = 5.85819814e-002 - fparams[64][6] = 4.14243130e-002 - fparams[64][7] = 5.06771477e-002 - fparams[64][8] = 2.61036728e+000 - fparams[64][9] = 1.99344244e+001 - fparams[64][10] = 4.20526863e-001 - fparams[64][11] = 2.85686240e-001 - fparams[65][0] = 2.59407462e-001 - fparams[65][1] = 5.04689354e-002 - fparams[65][2] = 3.16177855e+000 - fparams[65][3] = 1.23140183e+001 - fparams[65][4] = 2.75095751e+000 - fparams[65][5] = 4.38337626e-001 - fparams[65][6] = 2.79247686e+000 - fparams[65][7] = 2.23797309e+001 - fparams[65][8] = 3.85931001e-002 - fparams[65][9] = 4.87920992e-002 - fparams[65][10] = 4.10881708e-001 - fparams[65][11] = 2.77622892e-001 - fparams[66][0] = 3.16055396e+000 - fparams[66][1] = 1.25470414e+001 - fparams[66][2] = 2.82751709e+000 - fparams[66][3] = 4.67899094e-001 - fparams[66][4] = 2.75140255e-001 - fparams[66][5] = 5.23226982e-002 - fparams[66][6] = 4.00967160e-001 - fparams[66][7] = 2.67614884e-001 - fparams[66][8] = 2.63110834e+000 - fparams[66][9] = 2.19498166e+001 - fparams[66][10] = 3.61333817e-002 - fparams[66][11] = 4.68871497e-002 - fparams[67][0] = 2.88642467e-001 - fparams[67][1] = 5.40507687e-002 - fparams[67][2] = 2.90567296e+000 - fparams[67][3] = 4.97581077e-001 - fparams[67][4] = 3.15960159e+000 - fparams[67][5] = 1.27599505e+001 - fparams[67][6] = 3.91280259e-001 - fparams[67][7] = 2.58151831e-001 - fparams[67][8] = 2.48596038e+000 - fparams[67][9] = 2.15400972e+001 - fparams[67][10] = 3.37664478e-002 - fparams[67][11] = 4.50664323e-002 - fparams[68][0] = 3.15573213e+000 - fparams[68][1] = 1.29729009e+001 - fparams[68][2] = 3.11519560e-001 - fparams[68][3] = 5.81399387e-002 - fparams[68][4] = 2.97722406e+000 - fparams[68][5] = 5.31213394e-001 - fparams[68][6] = 3.81563854e-001 - fparams[68][7] = 2.49195776e-001 - fparams[68][8] = 2.40247532e+000 - fparams[68][9] = 2.13627616e+001 - fparams[68][10] = 3.15224214e-002 - fparams[68][11] = 4.33253257e-002 - fparams[69][0] = 3.15591970e+000 - fparams[69][1] = 1.31232407e+001 - fparams[69][2] = 3.22544710e-001 - fparams[69][3] = 5.97223323e-002 - fparams[69][4] = 3.05569053e+000 - fparams[69][5] = 5.61876773e-001 - fparams[69][6] = 2.92845100e-002 - fparams[69][7] = 4.16534255e-002 - fparams[69][8] = 3.72487205e-001 - fparams[69][9] = 2.40821967e-001 - fparams[69][10] = 2.27833695e+000 - fparams[69][11] = 2.10034185e+001 - fparams[70][0] = 3.10794704e+000 - fparams[70][1] = 6.06347847e-001 - fparams[70][2] = 3.14091221e+000 - fparams[70][3] = 1.33705269e+001 - fparams[70][4] = 3.75660454e-001 - fparams[70][5] = 7.29814740e-002 - fparams[70][6] = 3.61901097e-001 - fparams[70][7] = 2.32652051e-001 - fparams[70][8] = 2.45409082e+000 - fparams[70][9] = 2.12695209e+001 - fparams[70][10] = 2.72383990e-002 - fparams[70][11] = 3.99969597e-002 - fparams[71][0] = 3.11446863e+000 - fparams[71][1] = 1.38968881e+001 - fparams[71][2] = 5.39634353e-001 - fparams[71][3] = 8.91708508e-002 - fparams[71][4] = 3.06460915e+000 - fparams[71][5] = 6.79919563e-001 - fparams[71][6] = 2.58563745e-002 - fparams[71][7] = 3.82808522e-002 - fparams[71][8] = 2.13983556e+000 - fparams[71][9] = 1.80078788e+001 - fparams[71][10] = 3.47788231e-001 - fparams[71][11] = 2.22706591e-001 - fparams[72][0] = 3.01166899e+000 - fparams[72][1] = 7.10401889e-001 - fparams[72][2] = 3.16284788e+000 - fparams[72][3] = 1.38262192e+001 - fparams[72][4] = 6.33421771e-001 - fparams[72][5] = 9.48486572e-002 - fparams[72][6] = 3.41417198e-001 - fparams[72][7] = 2.14129678e-001 - fparams[72][8] = 1.53566013e+000 - fparams[72][9] = 1.55298698e+001 - fparams[72][10] = 2.40723773e-002 - fparams[72][11] = 3.67833690e-002 - fparams[73][0] = 3.20236821e+000 - fparams[73][1] = 1.38446369e+001 - fparams[73][2] = 8.30098413e-001 - fparams[73][3] = 1.18381581e-001 - fparams[73][4] = 2.86552297e+000 - fparams[73][5] = 7.66369118e-001 - fparams[73][6] = 2.24813887e-002 - fparams[73][7] = 3.52934622e-002 - fparams[73][8] = 1.40165263e+000 - fparams[73][9] = 1.46148877e+001 - fparams[73][10] = 3.33740596e-001 - fparams[73][11] = 2.05704486e-001 - fparams[74][0] = 9.24906855e-001 - fparams[74][1] = 1.28663377e-001 - fparams[74][2] = 2.75554557e+000 - fparams[74][3] = 7.65826479e-001 - fparams[74][4] = 3.30440060e+000 - fparams[74][5] = 1.34471170e+001 - fparams[74][6] = 3.29973862e-001 - fparams[74][7] = 1.98218895e-001 - fparams[74][8] = 1.09916444e+000 - fparams[74][9] = 1.35087534e+001 - fparams[74][10] = 2.06498883e-002 - fparams[74][11] = 3.38918459e-002 - fparams[75][0] = 1.96952105e+000 - fparams[75][1] = 4.98830620e+001 - fparams[75][2] = 1.21726619e+000 - fparams[75][3] = 1.33243809e-001 - fparams[75][4] = 4.10391685e+000 - fparams[75][5] = 1.84396916e+000 - fparams[75][6] = 2.90791978e-002 - fparams[75][7] = 2.84192813e-002 - fparams[75][8] = 2.30696669e-001 - fparams[75][9] = 1.90968784e-001 - fparams[75][10] = 6.08840299e-001 - fparams[75][11] = 1.37090356e+000 - fparams[76][0] = 2.06385867e+000 - fparams[76][1] = 4.05671697e+001 - fparams[76][2] = 1.29603406e+000 - fparams[76][3] = 1.46559047e-001 - fparams[76][4] = 3.96920673e+000 - fparams[76][5] = 1.82561596e+000 - fparams[76][6] = 2.69835487e-002 - fparams[76][7] = 2.84172045e-002 - fparams[76][8] = 2.31083999e-001 - fparams[76][9] = 1.79765184e-001 - fparams[76][10] = 6.30466774e-001 - fparams[76][11] = 1.38911543e+000 - fparams[77][0] = 2.21522726e+000 - fparams[77][1] = 3.24464090e+001 - fparams[77][2] = 1.37573155e+000 - fparams[77][3] = 1.60920048e-001 - fparams[77][4] = 3.78244405e+000 - fparams[77][5] = 1.78756553e+000 - fparams[77][6] = 2.44643240e-002 - fparams[77][7] = 2.82909938e-002 - fparams[77][8] = 2.36932016e-001 - fparams[77][9] = 1.70692368e-001 - fparams[77][10] = 6.48471412e-001 - fparams[77][11] = 1.37928390e+000 - fparams[78][0] = 9.84697940e-001 - fparams[78][1] = 1.60910839e-001 - fparams[78][2] = 2.73987079e+000 - fparams[78][3] = 7.18971667e-001 - fparams[78][4] = 3.61696715e+000 - fparams[78][5] = 1.29281016e+001 - fparams[78][6] = 3.02885602e-001 - fparams[78][7] = 1.70134854e-001 - fparams[78][8] = 2.78370726e-001 - fparams[78][9] = 1.49862703e+000 - fparams[78][10] = 1.52124129e-002 - fparams[78][11] = 2.83510822e-002 - fparams[79][0] = 9.61263398e-001 - fparams[79][1] = 1.70932277e-001 - fparams[79][2] = 3.69581030e+000 - fparams[79][3] = 1.29335319e+001 - fparams[79][4] = 2.77567491e+000 - fparams[79][5] = 6.89997070e-001 - fparams[79][6] = 2.95414176e-001 - fparams[79][7] = 1.63525510e-001 - fparams[79][8] = 3.11475743e-001 - fparams[79][9] = 1.39200901e+000 - fparams[79][10] = 1.43237267e-002 - fparams[79][11] = 2.71265337e-002 - fparams[80][0] = 1.29200491e+000 - fparams[80][1] = 1.83432865e-001 - fparams[80][2] = 2.75161478e+000 - fparams[80][3] = 9.42368371e-001 - fparams[80][4] = 3.49387949e+000 - fparams[80][5] = 1.46235654e+001 - fparams[80][6] = 2.77304636e-001 - fparams[80][7] = 1.55110144e-001 - fparams[80][8] = 4.30232810e-001 - fparams[80][9] = 1.28871670e+000 - fparams[80][10] = 1.48294351e-002 - fparams[80][11] = 2.61903834e-002 - fparams[81][0] = 3.75964730e+000 - fparams[81][1] = 1.35041513e+001 - fparams[81][2] = 3.21195904e+000 - fparams[81][3] = 6.66330993e-001 - fparams[81][4] = 6.47767825e-001 - fparams[81][5] = 9.22518234e-002 - fparams[81][6] = 2.76123274e-001 - fparams[81][7] = 1.50312897e-001 - fparams[81][8] = 3.18838810e-001 - fparams[81][9] = 1.12565588e+000 - fparams[81][10] = 1.31668419e-002 - fparams[81][11] = 2.48879842e-002 - fparams[82][0] = 1.00795975e+000 - fparams[82][1] = 1.17268427e-001 - fparams[82][2] = 3.09796153e+000 - fparams[82][3] = 8.80453235e-001 - fparams[82][4] = 3.61296864e+000 - fparams[82][5] = 1.47325812e+001 - fparams[82][6] = 2.62401476e-001 - fparams[82][7] = 1.43491014e-001 - fparams[82][8] = 4.05621995e-001 - fparams[82][9] = 1.04103506e+000 - fparams[82][10] = 1.31812509e-002 - fparams[82][11] = 2.39575415e-002 - fparams[83][0] = 1.59826875e+000 - fparams[83][1] = 1.56897471e-001 - fparams[83][2] = 4.38233925e+000 - fparams[83][3] = 2.47094692e+000 - fparams[83][4] = 2.06074719e+000 - fparams[83][5] = 5.72438972e+001 - fparams[83][6] = 1.94426023e-001 - fparams[83][7] = 1.32979109e-001 - fparams[83][8] = 8.22704978e-001 - fparams[83][9] = 9.56532528e-001 - fparams[83][10] = 2.33226953e-002 - fparams[83][11] = 2.23038435e-002 - fparams[84][0] = 1.71463223e+000 - fparams[84][1] = 9.79262841e+001 - fparams[84][2] = 2.14115960e+000 - fparams[84][3] = 2.10193717e-001 - fparams[84][4] = 4.37512413e+000 - fparams[84][5] = 3.66948812e+000 - fparams[84][6] = 2.16216680e-002 - fparams[84][7] = 1.98456144e-002 - fparams[84][8] = 1.97843837e-001 - fparams[84][9] = 1.33758807e-001 - fparams[84][10] = 6.52047920e-001 - fparams[84][11] = 7.80432104e-001 - fparams[85][0] = 1.48047794e+000 - fparams[85][1] = 1.25943919e+002 - fparams[85][2] = 2.09174630e+000 - fparams[85][3] = 1.83803008e-001 - fparams[85][4] = 4.75246033e+000 - fparams[85][5] = 4.19890596e+000 - fparams[85][6] = 1.85643958e-002 - fparams[85][7] = 1.81383503e-002 - fparams[85][8] = 2.05859375e-001 - fparams[85][9] = 1.33035404e-001 - fparams[85][10] = 7.13540948e-001 - fparams[85][11] = 7.03031938e-001 - fparams[86][0] = 6.30022295e-001 - fparams[86][1] = 1.40909762e-001 - fparams[86][2] = 3.80962881e+000 - fparams[86][3] = 3.08515540e+001 - fparams[86][4] = 3.89756067e+000 - fparams[86][5] = 6.51559763e-001 - fparams[86][6] = 2.40755100e-001 - fparams[86][7] = 1.08899672e-001 - fparams[86][8] = 2.62868577e+000 - fparams[86][9] = 6.42383261e+000 - fparams[86][10] = 3.14285931e-002 - fparams[86][11] = 2.42346699e-002 - fparams[87][0] = 5.23288135e+000 - fparams[87][1] = 8.60599536e+000 - fparams[87][2] = 2.48604205e+000 - fparams[87][3] = 3.04543982e-001 - fparams[87][4] = 3.23431354e-001 - fparams[87][5] = 3.87759096e-002 - fparams[87][6] = 2.55403596e-001 - fparams[87][7] = 1.28717724e-001 - fparams[87][8] = 5.53607228e-001 - fparams[87][9] = 5.36977452e-001 - fparams[87][10] = 5.75278889e-003 - fparams[87][11] = 1.29417790e-002 - fparams[88][0] = 1.44192685e+000 - fparams[88][1] = 1.18740873e-001 - fparams[88][2] = 3.55291725e+000 - fparams[88][3] = 1.01739750e+000 - fparams[88][4] = 3.91259586e+000 - fparams[88][5] = 6.31814783e+001 - fparams[88][6] = 2.16173519e-001 - fparams[88][7] = 9.55806441e-002 - fparams[88][8] = 3.94191605e+000 - fparams[88][9] = 3.50602732e+001 - fparams[88][10] = 4.60422605e-002 - fparams[88][11] = 2.20850385e-002 - fparams[89][0] = 1.45864127e+000 - fparams[89][1] = 1.07760494e-001 - fparams[89][2] = 4.18945405e+000 - fparams[89][3] = 8.89090649e+001 - fparams[89][4] = 3.65866182e+000 - fparams[89][5] = 1.05088931e+000 - fparams[89][6] = 2.08479229e-001 - fparams[89][7] = 9.09335557e-002 - fparams[89][8] = 3.16528117e+000 - fparams[89][9] = 3.13297788e+001 - fparams[89][10] = 5.23892556e-002 - fparams[89][11] = 2.08807697e-002 - fparams[90][0] = 1.19014064e+000 - fparams[90][1] = 7.73468729e-002 - fparams[90][2] = 2.55380607e+000 - fparams[90][3] = 6.59693681e-001 - fparams[90][4] = 4.68110181e+000 - fparams[90][5] = 1.28013896e+001 - fparams[90][6] = 2.26121303e-001 - fparams[90][7] = 1.08632194e-001 - fparams[90][8] = 3.58250545e-001 - fparams[90][9] = 4.56765664e-001 - fparams[90][10] = 7.82263950e-003 - fparams[90][11] = 1.62623474e-002 - fparams[91][0] = 4.68537504e+000 - fparams[91][1] = 1.44503632e+001 - fparams[91][2] = 2.98413708e+000 - fparams[91][3] = 5.56438592e-001 - fparams[91][4] = 8.91988061e-001 - fparams[91][5] = 6.69512914e-002 - fparams[91][6] = 2.24825384e-001 - fparams[91][7] = 1.03235396e-001 - fparams[91][8] = 3.04444846e-001 - fparams[91][9] = 4.27255647e-001 - fparams[91][10] = 9.48162708e-003 - fparams[91][11] = 1.77730611e-002 - fparams[92][0] = 4.63343606e+000 - fparams[92][1] = 1.63377267e+001 - fparams[92][2] = 3.18157056e+000 - fparams[92][3] = 5.69517868e-001 - fparams[92][4] = 8.76455075e-001 - fparams[92][5] = 6.88860012e-002 - fparams[92][6] = 2.21685477e-001 - fparams[92][7] = 9.84254550e-002 - fparams[92][8] = 2.72917100e-001 - fparams[92][9] = 4.09470917e-001 - fparams[92][10] = 1.11737298e-002 - fparams[92][11] = 1.86215410e-002 - fparams[93][0] = 4.56773888e+000 - fparams[93][1] = 1.90992795e+001 - fparams[93][2] = 3.40325179e+000 - fparams[93][3] = 5.90099634e-001 - fparams[93][4] = 8.61841923e-001 - fparams[93][5] = 7.03204851e-002 - fparams[93][6] = 2.19728870e-001 - fparams[93][7] = 9.36334280e-002 - fparams[93][8] = 2.38176903e-001 - fparams[93][9] = 3.93554882e-001 - fparams[93][10] = 1.38306499e-002 - fparams[93][11] = 1.94437286e-002 - fparams[94][0] = 5.45671123e+000 - fparams[94][1] = 1.01892720e+001 - fparams[94][2] = 1.11687906e-001 - fparams[94][3] = 3.98131313e-002 - fparams[94][4] = 3.30260343e+000 - fparams[94][5] = 3.14622212e-001 - fparams[94][6] = 1.84568319e-001 - fparams[94][7] = 1.04220860e-001 - fparams[94][8] = 4.93644263e-001 - fparams[94][9] = 4.63080540e-001 - fparams[94][10] = 3.57484743e+000 - fparams[94][11] = 2.19369542e+001 - fparams[95][0] = 5.38321999e+000 - fparams[95][1] = 1.07289857e+001 - fparams[95][2] = 1.23343236e-001 - fparams[95][3] = 4.15137806e-002 - fparams[95][4] = 3.46469090e+000 - fparams[95][5] = 3.39326208e-001 - fparams[95][6] = 1.75437132e-001 - fparams[95][7] = 9.98932346e-002 - fparams[95][8] = 3.39800073e+000 - fparams[95][9] = 2.11601535e+001 - fparams[95][10] = 4.69459519e-001 - fparams[95][11] = 4.51996970e-001 - fparams[96][0] = 5.38402377e+000 - fparams[96][1] = 1.11211419e+001 - fparams[96][2] = 3.49861264e+000 - fparams[96][3] = 3.56750210e-001 - fparams[96][4] = 1.88039547e-001 - fparams[96][5] = 5.39853583e-002 - fparams[96][6] = 1.69143137e-001 - fparams[96][7] = 9.60082633e-002 - fparams[96][8] = 3.19595016e+000 - fparams[96][9] = 1.80694389e+001 - fparams[96][10] = 4.64393059e-001 - fparams[96][11] = 4.36318197e-001 - fparams[97][0] = 3.66090688e+000 - fparams[97][1] = 3.84420906e-001 - fparams[97][2] = 2.03054678e-001 - fparams[97][3] = 5.48547131e-002 - fparams[97][4] = 5.30697515e+000 - fparams[97][5] = 1.17150262e+001 - fparams[97][6] = 1.60934046e-001 - fparams[97][7] = 9.21020329e-002 - fparams[97][8] = 3.04808401e+000 - fparams[97][9] = 1.73525367e+001 - fparams[97][10] = 4.43610295e-001 - fparams[97][11] = 4.27132359e-001 - fparams[98][0] = 3.94150390e+000 - fparams[98][1] = 4.18246722e-001 - fparams[98][2] = 5.16915345e+000 - fparams[98][3] = 1.25201788e+001 - fparams[98][4] = 1.61941074e-001 - fparams[98][5] = 4.81540117e-002 - fparams[98][6] = 4.15299561e-001 - fparams[98][7] = 4.24913856e-001 - fparams[98][8] = 2.91761325e+000 - fparams[98][9] = 1.90899693e+001 - fparams[98][10] = 1.51474927e-001 - fparams[98][11] = 8.81568925e-002 - fparams[99][0] = 4.09780623e+000 - fparams[99][1] = 4.46021145e-001 - fparams[99][2] = 5.10079393e+000 - fparams[99][3] = 1.31768613e+001 - fparams[99][4] = 1.74617289e-001 - fparams[99][5] = 5.02742829e-002 - fparams[99][6] = 2.76774658e+000 - fparams[99][7] = 1.84815393e+001 - fparams[99][8] = 1.44496639e-001 - fparams[99][9] = 8.46232592e-002 - fparams[99][10] = 4.02772109e-001 - fparams[99][11] = 4.17640100e-001 - fparams[100][0] = 4.24934820e+000 - fparams[100][1] = 4.75263933e-001 - fparams[100][2] = 5.03556594e+000 - fparams[100][3] = 1.38570834e+001 - fparams[100][4] = 1.88920613e-001 - fparams[100][5] = 5.26975158e-002 - fparams[100][6] = 3.94356058e-001 - fparams[100][7] = 4.11193751e-001 - fparams[100][8] = 2.61213100e+000 - fparams[100][9] = 1.78537905e+001 - fparams[100][10] = 1.38001927e-001 - fparams[100][11] = 8.12774434e-002 - fparams[101][0] = 2.00942931e-001 - fparams[101][1] = 5.48366518e-002 - fparams[101][2] = 4.40119869e+000 - fparams[101][3] = 5.04248434e-001 - fparams[101][4] = 4.97250102e+000 - fparams[101][5] = 1.45721366e+001 - fparams[101][6] = 2.47530599e+000 - fparams[101][7] = 1.72978308e+001 - fparams[101][8] = 3.86883197e-001 - fparams[101][9] = 4.05043898e-001 - fparams[101][10] = 1.31936095e-001 - fparams[101][11] = 7.80821071e-002 - fparams[102][0] = 2.16052899e-001 - fparams[102][1] = 5.83584058e-002 - fparams[102][2] = 4.91106799e+000 - fparams[102][3] = 1.53264212e+001 - fparams[102][4] = 4.54862870e+000 - fparams[102][5] = 5.34434760e-001 - fparams[102][6] = 2.36114249e+000 - fparams[102][7] = 1.68164803e+001 - fparams[102][8] = 1.26277292e-001 - fparams[102][9] = 7.50304633e-002 - fparams[102][10] = 3.81364501e-001 - fparams[102][11] = 3.99305852e-001 - fparams[103][0] = 4.86738014e+000 - fparams[103][1] = 1.60320520e+001 - fparams[103][2] = 3.19974401e-001 - fparams[103][3] = 6.70871138e-002 - fparams[103][4] = 4.58872425e+000 - fparams[103][5] = 5.77039373e-001 - fparams[103][6] = 1.21482448e-001 - fparams[103][7] = 7.22275899e-002 - fparams[103][8] = 2.31639872e+000 - fparams[103][9] = 1.41279737e+001 - fparams[103][10] = 3.79258137e-001 - fparams[103][11] = 3.89973484e-001 - return fparams[Z] - - -def generate_k_grid(shape, spacing): - ki = 2 * np.pi * np.fft.fftfreq(shape[0],spacing[0]) - kj = 2 * np.pi * np.fft.fftfreq(shape[1],spacing[1]) - Kj, Ki = np.meshgrid(kj,ki) - return Ki, Kj, np.sqrt(Ki**2 + Kj**2) - -def generate_atom(Z, Ksq): - - coeffs = fParams(Z) - - # This will be the k-space representation of the object function - scattering_factors = np.zeros(Ksq.shape,dtype=np.complex64) - - for m in range(0, 3): - a = 2*m - b = a+1 - c = a + 6 - d = b + 6 - # Keep in mind that these constants are in angstrom-related units. - # for a; m=0,2,4 -> A^-1 - # for b; m=1,3,5 -> A^-2 - # for c; m=6,8,10 -> A - # for d; m=7,9,11 -> A^2 - - # This is the functional form of the parameterization - scattering_factors += (1e10*coeffs[a])/(Ksq+1e20*coeffs[b]) - scattering_factors += 1e-10*coeffs[c]*np.exp(-1e-20*coeffs[d] * Ksq) - - # This is the real-space distribution - return np.fft.ifft2(scattering_factors) - - diff --git a/src/cdtools/tools/data/__init__.py b/src/cdtools/tools/data/__init__.py index 6ea91aa..a075f60 100644 --- a/src/cdtools/tools/data/__init__.py +++ b/src/cdtools/tools/data/__init__.py @@ -1 +1,2 @@ from cdtools.tools.data.data import * +from cdtools.tools.data.data import __all__, __doc__ diff --git a/src/cdtools/tools/image_processing/__init__.py b/src/cdtools/tools/image_processing/__init__.py index e6a2982..fc35d22 100644 --- a/src/cdtools/tools/image_processing/__init__.py +++ b/src/cdtools/tools/image_processing/__init__.py @@ -1 +1,2 @@ from cdtools.tools.image_processing.image_processing import * +from cdtools.tools.image_processing.image_processing import __all__, __doc__ diff --git a/src/cdtools/tools/initializers/__init__.py b/src/cdtools/tools/initializers/__init__.py index de6e2df..f1e31ff 100644 --- a/src/cdtools/tools/initializers/__init__.py +++ b/src/cdtools/tools/initializers/__init__.py @@ -1 +1,2 @@ from cdtools.tools.initializers.initializers import * +from cdtools.tools.initializers.initializers import __all__, __doc__ diff --git a/src/cdtools/tools/interactions/__init__.py b/src/cdtools/tools/interactions/__init__.py index ce03f39..e8f54a3 100644 --- a/src/cdtools/tools/interactions/__init__.py +++ b/src/cdtools/tools/interactions/__init__.py @@ -1 +1,2 @@ from cdtools.tools.interactions.interactions import * +from cdtools.tools.interactions.interactions import __all__, __doc__ diff --git a/src/cdtools/tools/losses/__init__.py b/src/cdtools/tools/losses/__init__.py index 7b0242a..3d58451 100644 --- a/src/cdtools/tools/losses/__init__.py +++ b/src/cdtools/tools/losses/__init__.py @@ -1 +1,2 @@ from cdtools.tools.losses.losses import * +from cdtools.tools.losses.losses import __all__, __doc__ diff --git a/src/cdtools/tools/measurements/__init__.py b/src/cdtools/tools/measurements/__init__.py index 6c2a003..81187f4 100644 --- a/src/cdtools/tools/measurements/__init__.py +++ b/src/cdtools/tools/measurements/__init__.py @@ -1 +1,2 @@ from cdtools.tools.measurements.measurements import * +from cdtools.tools.measurements.measurements import __all__, __doc__ diff --git a/src/cdtools/tools/plotting/__init__.py b/src/cdtools/tools/plotting/__init__.py index c9f1c55..87bc53a 100644 --- a/src/cdtools/tools/plotting/__init__.py +++ b/src/cdtools/tools/plotting/__init__.py @@ -1,2 +1,3 @@ from cdtools.tools.plotting.plotting import * +from cdtools.tools.plotting.plotting import __all__, __doc__ diff --git a/src/cdtools/tools/propagators/__init__.py b/src/cdtools/tools/propagators/__init__.py index 8ca3ad2..dbe8ac3 100644 --- a/src/cdtools/tools/propagators/__init__.py +++ b/src/cdtools/tools/propagators/__init__.py @@ -1 +1,2 @@ from cdtools.tools.propagators.propagators import * +from cdtools.tools.propagators.propagators import __all__, __doc__ diff --git a/tests/models/test_simple_ptycho.py b/tests/models/test_simple_ptycho.py index 770b1a0..f74dd0d 100644 --- a/tests/models/test_simple_ptycho.py +++ b/tests/models/test_simple_ptycho.py @@ -1,6 +1,8 @@ +import pytest import cdtools from matplotlib import pyplot as plt +@pytest.mark.slow def test_simple_ptycho(lab_ptycho_cxi, reconstruction_device, show_plot): dataset = cdtools.datasets.Ptycho2DDataset.from_cxi(lab_ptycho_cxi)