Summary of changes in STIR release 6.3
Overall summary
Patch release info
Summary for end users (also to be read by developers)
New functionality
General
-
Several 2D analytic reconstruction algorithms were added for PET (i.e. inverting the 2D Radon transform)
and parallel beam SPECT (inverting the 2D attenuated Radon transform). The latter
allow quantitatively correct analytic reconstruction of SPECT data (after scatter correction).
-
The Spline Reconstruction Technique (SRT) algorithm has been added in 2 different versions:
SRT2D for PET and SRT2DSPECT for SPECT.
The reference for the implemented algorithms is:
Fokas, A. S., A. Iserles, and V. Marinakis.
Reconstruction algorithm for single photon emission computed tomography and its numerical
implementation.
Journal of the Royal Society Interface* 3.6 (2006): 45-54.
-
GRD2D for PET is a direct Fourier method using regridding with Kaiser-Bessel functions.
-
DDSR2D for parallel beam SPECT uses Hilbert transforms in projection space.
The reference for the implementation of these algorithms is:
Dimitra Kyriakopoulou, Analytical and Numerical Aspects of Tomography,
PhD thesis, University College London (UCL), 2024,
Available at:
discovery.ucl.ac.uk/id/eprint/10202525/.
PR #1420 and PR #1595.
-
Wiener and Gamma filters were added.
PR #1420.
-
ScatterSimulation can now downsample the scanner transaxially (crystals per ring) for
BlocksOnCylindrical,
scanners, which speeds up ScatterEstimation considerably. By default, downsampling the detectors per
reading
is disabled for backwards compatibility.
PR #1291
-
The priors code has been refactored to provide two common, parallelized base classes for CPU and GPU implementations (
GibbsPenalty and CudaGibbsPenalty).
On CPU, we introduce GibbsQuadraticPenalty and GibbsRelativeDifferencePenalty, which inherit from the parallelized GibbsPenalty base class (now parallelized using OpenMP).
GPU implementations are also provided as CudaGibbsQuadraticPenalty and CudaGibbsRelativeDifferencePenalty.
Currently, the new Gibbs penalties are still missing the paraboloidal surrogates related method implementations. They provide two new methods: compute_gradient_times_input and compute_Hessian_diagonal.
PR #1629
-
Data from GE Discovery MI systems in RDF9 should now be readable. TOF information on these scanners has also been
added.
However, projection data is currently still always returned as non-TOF (but list-mode data is read as TOF).
PR #1503
-
Added the ability to set a forward projector for mask projection in the
ScatterEstimation class.
PR #1530
-
Duration in sinogram interfile/exam_info obtained from
LmToProjData/lm_to_projdata has the
correct value if we unlist all the events. This is not true for ROOT files
PR #1519
-
LmToProjData class/lm_to_projdata utility now no longer requires a template projection data. If none is
specified, it will use the proj_data_info from the input list-mode.
Warning for some scanners with TOF capabilities, this will result in very large projection data (possibly
larger than the default from the vendor).
PR #1315
-
Adapt the SPECTUB projector to handle data with only a subset of the views (constructed using
ProjData::get_subsets().
This is useful for SIRF/CIL applications using stochastic optimisation.
PR #1596
Python
-
"Container" classes such as
FloatVoxelsOnCartesianGrid, ProjDataInMemory
and array-classes now have numerical operations properly defined, for instance
a = b + c and a -= 3. Note that a = 1 + b is not
yet available.
PR #1630
-
The above "container" classes now have an extra member `as_array()` which returns a numpy
ndarray. This
is equivalent to `stirextra.to_numpy()` which will become deprecated later. In addition, the
fill() method now directly accepts an ndarray, avoiding the need to go via an iterator.
These additions also make it easier to prt SIRF python code to STIR.
PR #1632
-
Added a Python script to convert e7tools generated Siemens Biograph Vision 600 sinograms to STIR compatible format.
PR #1593
Utilities
-
stir_timings has now an extra option to parse a par-file for a projector-pair.
Changed functionality
-
In previous versions, when reading data/images where the radionuclide was not set, a default was used (F18 for
PET, Tcm99 for SPECT).
This led to surprising (and sometimes wrong) behaviour. The radionuclide is now kept as "unknown".
PR #1574
-
Default ECAT scanner configurations updated to use a negative intrinsic tilt.
-
When computing the sensitivity images in
PoissonLogLikelihoodWithLinearModelForMeanAndProjData,
we now avoid creating an extra ProjDataInMemory in most cases (there are still some corner
cases for TOF data when using non-TOF projector for the sensitivity, but then the memory overhead is small).
This enables LAFOV PET reconstructions with the "ray tracing" matrix (we use less memory, and we avoid running into a current
ProjDataInMemory limitation on the number of bins).
PR #1716
-
Boost format was replaced by `std::format` for formatting strings. If C++20 or newer is
not yet used, a work-around is in place by using the [{fmt} library](https://github.com/fmtlib/fmt/)
(included as as a git submodule).
Import
stir/format.h and then use the format() function to create strings containing various variables. If the format string is not known at compile time,
use runtime_format() instead.
Check the updated STIR-developers-overview.
PR #1591 and PR #1605
Changes to examples
-
Python example
plot_sinogram_profiles.py has been renamed to plot_projdata_profiles.py
and generalised to work with TOF dimensions etc. A small pytest has been added as well.
PR #1370
-
Python example
ProjDataVisualisation.py now has a vmax slider.
PR #1568
Bug fixes
-
Fixed a bug in the scatter estimation code (introduced in release 5.1.0) if input data is 3D and "cylindrical"
(there was no bug for "blocksoncylindrical" data).
The scatter estimation runs on data constructed via SSRB. However, the attenuation correction factors were
incorrectly obtained with adding of oblique segments (as opposed to averaging).
This resulted in intermediate images that had the wrong attenuation correction which were approximately
num_segments times larger. This was compensated by the tail-fitting, but resulted in unexpected scale factors
(scale factors were around 1/num_segments times what was expected).
This means that if you used the "min/max scale factor" feature in the scatter estimate, you will have to adjust
your threshold values. Expected scatter tail-fitting scale factors should now be restored to ~1-1.5 (depending on
the amount of multiple and out-of-FOV scatter).
See Issue #1532 for more detail. Fixed by using averaging
functionality of SSRB instead of adding segments for attenuation correction factors.
PR #1531
-
Fixed a bug in the distributed LM computation code (introduced in 6.1) that neglected to accumulate outputs when
not built with OpenMP.
See PR #1566.
-
Fixed bugs in
accumulate_sub_Hessian_times_input and accumulate_sub_Hessian_times_input
(and hence the non-subset versions) for objective functions when the prior is not zero.
See PR #1649 and PR #1651.
Build system
- Enable more diagnostics in CMake when finding CERN's ROOT (we used to silence them)
PR #1552
- Use OpenMP by default
- Introduce advanced variable MINI_STIR defaulting to OFF for developers.
This will build a heavily reduced version of STIR which can speed up development time.
PR #1584
Known problems
See our issue tracker.
What is new for developers (aside from what should be obvious from the above):
New functionality
-
ProjDataInMemory read_from_file method now returns a ProjDataInMemory
object.
-
Array::resize and Array::grow argument initialise_with_0 usage
fixed.
Changed functionality
-
In C++, "Container" classes such as
VoxelsOnCartesianGrid, ProjDataInMemory
and array-classes now have numerical operations that return objects of the correct type.
(Previously, it was a base-class such as NumericVectorWithOffset, float>).
PR #1630
-
Made 2 (deprecated) members of
ProjDataInfoBlocksOnCylindricalNoArcCorr private
and do some clean-up of which files to include.
PR #1556
-
LmToProjData::get_template_proj_data_info_sptr() is now a const member returning
a shared_ptr<const ProjDataInfo>.
PR #1315
-
As
stir::Array template arguments might change in the future,
it is now recommended to include stir/ArrayFwd.h when using forward
declaration and use the ArrayType template-alias in places where
a rectangular array that might live on a GPU is intended.
PR #1589
-
Array copy constructor now also uses contiguous memory allocation (as opposed to a sequence of 1D vectors).
PR #1592.
Bug fixes
- Fixed minor incompatibility with gcc-14 and clang-18 by adding an extra include file.
PR #1552
-
Changed the way that some SWIG work-arounds are implemented, avoiding the SWIG-generated
wrapper to be compiled with the
SWIG preprocessor symbol.
PR #1647
New Deprecations and renames
-
truncate_end_planes will be removed in v7.0
-
legacy compatibility with version 3, 4 and 5 will be removed in v7.0.
CMake options STIR_PROJECTORS_AS_V3, STIR_LEGACY_IGNORE_VIEW_OFFSET and
STIR_ROOT_ROTATION_AS_V4 will therefore be removed.
-
Starting from v7.0,
GeneralizedPrior will be renamed to GeneralizedPenalty.
QuadraticPrior, RelativeDifferencePrior, and LogcoshPrior will be removed in favor of the new GibbsPenalty framework.
Issue #1426
Test changes
Python tests
-
Tests for numerical operations for the "container" classes were added in the same PR as the code.
PR #1630
C++ tests
recon_test_pack