Command Line Interface
DECAES provides a command line interface (CLI) for calling the main analysis functions: T2mapSEcorr
for computing $T_2$-distributions, and T2partSEcorr
for running $T_2$-parts analysis on the resulting $T_2$-distributions for computing measures such as the myelin water fraction.
Using the CLI
Assuming you have DECAES installed, there are two equivalent ways to use the CLI:
1. Helper script: Create a simple Julia script which calls the entrypoint function main
provided by this package. For example, save the following code in a Julia script called decaes.jl
(or, download the script located here):
using DECAES # load the package
main() # call command line interface
An image file image.nii
can be passed to DECAES by running this script with julia
from the command line:
$ julia decaes.jl -- image.nii <COMMAND LINE ARGS>
2. Julia -e
flag: The contents of the above script can equivalently be passed directly to julia
using the -e
(for "evaluate") flag:
$ julia -e 'using DECAES; main()' -- image.nii <COMMAND LINE ARGS>
Either way of calling the CLI forwards the arguments <COMMAND LINE ARGS>
to the entrypoint function main
. Available command line arguments are detailed in the Arguments section.
For the remainder of this section, we will make use of the decaes.jl
script from option 1.
File types
Input files must be one of the following file types:
- NIfTI file with extension
.nii
, or gzip compressed NIfTI file with extension.nii.gz
. See NIfTI.jl for more information. - MATLAB file with extension
.mat
. Note:.mat
files saved in the oldest formatv4
are not supported, but all newer formats (v6
,v7
, andv7.3
) are supported. See MAT.jl for more information. - Philips PAR/REC file pair with extensions
.par
and.rec
(or.PAR
and.REC
). - Philips XML/REC file pair with extensions
.xml
and.rec
(or.XML
and.REC
).
All output files are saved as .mat
files in format v7.3
.
If your data is in DICOM format, the freely available dcm2niix
tool is able to convert DICOM files into NIfTI format
- Input files are interpreted as 4D arrays (or 3D arrays for mask files) when loaded; ensure that the underlying data is stored with the first three dimensions as (row, column, slice), and the last dimension as echo (or $T_2$ bin, or omitted for mask files)
- Images read from NIfTI and PAR/XML/REC files are coerced into the appropriate dimension; errors or unexpected behaviour may occur if the data is not stored with the correct dimensions
- MATLAB files are searched for arrays with the appropriate dimension; the first such array that is found is used, otherwise an error will occur. Multiple 3D/4D arrays should not be stored in the same
.mat
file)
Arguments
Available command line arguments are broken into four categories:
- Positional arguments: these are the input files. Input files are typically placed at the beginning of
<COMMAND LINE ARGS>
. - Optional arguments: settings governing the analysis pipeline. See below for details.
T2mapSEcorr
/T2partSEcorr
arguments: settings for computing the $T_2$-distribution and subsequent $T_2$-parts analysis. Required arguments are listed first; see below for the full parameter list, and seeT2mapSEcorr
andT2partSEcorr
for parameter descriptions. Note: if no default is shown, the parameter is unused by default.- B1 correction and stimulated echo correction: settings for controlling B1 correction and stimulated echo correction. These settings typically need not be modified. However, the following options are noteworthy:
--SetFlipAngle
for skipping B1 correction; and--RefConAngle
for enabling stimulated echo correction. - Additional save options: optional additional output maps
- BET arguments: settings for governing automatic brain mask generation using the BET brain extraction tool; see below for details.
usage: <PROGRAM> [-m MASK [MASK...]] [-o OUTPUT] [--T2map] [--T2part] [-q] [--dry] [--legacy] [--MatrixSize MATRIXSIZE MATRIXSIZE MATRIXSIZE] [--nTE NTE] [--TE TE] [--nT2 NT2] [--T2Range T2RANGE T2RANGE] [--SPWin SPWIN SPWIN] [--MPWin MPWIN MPWIN] [--T1 T1] [--Reg REG] [--Chi2Factor CHI2FACTOR] [--Sigmoid SIGMOID] [--Threshold THRESHOLD] [--nRefAngles NREFANGLES] [--nRefAnglesMin NREFANGLESMIN] [--MinRefAngle MINREFANGLE] [--SetFlipAngle SETFLIPANGLE] [--RefConAngle REFCONANGLE] [--SaveDecayCurve] [--SaveNNLSBasis] [--SaveRegParam] [--SaveResidualNorm] [--bet] [--betargs BETARGS] [--betpath BETPATH] input... positional arguments: input one or more input filenames. Valid file types are limited to: .mat, .nii, .nii.gz, .par, .xml, and .rec optional arguments: -m, --mask MASK [MASK...] one or more mask filenames. Masks are loaded and subsequently applied to the corresponding input files via elementwise multiplication. The number of mask files must equal the number of input files. Valid file types are the same as for input files, and are limited to: .mat, .nii, .nii.gz, .par, .xml, and .rec -o, --output OUTPUT output directory. If not specified, output file(s) will be stored in the same location as the corresponding input file(s). Outputs are stored with the same basename as the input files with additional suffixes; see --T2map and --T2part --T2map call T2mapSEcorr to compute T2 distributions from 4D multi spin-echo input images. T2 distributions and T2 maps produced by T2mapSEcorr are saved as MAT files with extensions .t2dist.mat and .t2maps.mat --T2part call T2partSEcorr to analyze 4D T2 distributions to produce parameter maps. If --T2map is also passed, input 4D arrays are interpreted as multi spin-echo images and T2 distributions are first computed by T2mapSEcorr. If only --T2part is passed, input 4D arrays are interpreted as T2 distributions and only T2partSEcorr is called. Output T2 parts are saved as a MAT file with extension .t2parts.mat -q, --quiet suppress printing to the terminal. Note: all terminal outputs, including errors and warnings, are still printed to the log file --dry execute dry run of processing without saving any results --legacy use legacy settings and algorithms from the original MATLAB pipeline. This ensures that the same T2-distributions and T2-parts will be produced as those from MATLAB. Note that execution time will be much slower, and less robust algorithms will be used. T2mapSEcorr/T2partSEcorr arguments: --MatrixSize MATRIXSIZE MATRIXSIZE MATRIXSIZE first three dimensions of input 4D image. Inferred automatically (type: Int64) --nTE NTE number of echoes in input signal. Inferred automatically when --T2map is passed (type: Int64) --TE TE inter-echo spacing (Units: seconds). Required when --T2map is passed (type: Float64) --nT2 NT2 number of T2 components used in the multi-exponential analysis. Required when --T2map is passed. Inferred from fourth dimension of input image if only --T2part is passed (type: Int64) --T2Range T2RANGE T2RANGE minimum and maximum T2 values (Units: seconds). T2 components are logarithmically spaced between these bounds. Required parameter. (type: Float64) --SPWin SPWIN SPWIN minimum and maximum T2 values of the short peak window (Units: seconds). Required parameter when --T2part is passed (type: Float64) --MPWin MPWIN MPWIN minimum and maximum T2 values of the middle peak window (Units: seconds). Required parameter when --T2part is passed (type: Float64) --T1 T1 assumed value of longitudinal T1 relaxation (Units: seconds). (type: Float64) --Reg REG routine used for choosing regularization parameter. One of "none", "chi2", "gcv", or "lcurve", representing no regularization, --Chi2Factor based Tikhonov regularization, generalized cross-validation based regularization, and L-curve based regularization, respectively. --Chi2Factor CHI2FACTOR if --Reg="chi2", the T2 distribution is regularized such that the chi^2 goodness of fit is increased by a multiplicative factor --Chi2Factor relative to the unregularized solution (type: Float64) --Sigmoid SIGMOID replace the hard upper limit cutoff time of the short peak window, --SPWin[2], with a smoothed sigmoidal cutoff function, f, scaled and shifted such that f(--SPWin[2] +/- --Sigmoid) = 0.5 -/+ 0.4. --Sigmoid is the time scale of the smoothing (Units: seconds) (type: Float64) --Threshold THRESHOLD first echo intensity cutoff for empty voxels. Processing is skipped for voxels with intensity <= --Threshold (type: Float64) B1 correction and stimulated echo correction: --nRefAngles NREFANGLES in estimating the local refocusing flip angle to correct for B1 inhomogeneities, up to --nRefAngles angles in the range [--MinRefAngle, 180] are explicitly checked. The optimal angle is then determined through interpolation from these --nRefAngles observations. (type: Int64) --nRefAnglesMin NREFANGLESMIN initial number of angles to check during flip angle estimation before refinement near likely optima. Setting --nRefAnglesMin equal to --nRefAngles forces all angles to be checked. (type: Int64) --MinRefAngle MINREFANGLE minimum refocusing angle for flip angle estimation (Units: degrees). (type: Float64) --SetFlipAngle SETFLIPANGLE to skip B1 inhomogeneity correction, use --SetFlipAngle to assume a fixed refocusing flip angle for all voxels (Units: degrees). (type: Float64) --RefConAngle REFCONANGLE refocusing pulse control angle for stimulated echo correction. Unlike B1 inhomogeneity correction, stimulated echo correction must be performed manually. By default, --RefConAngle is set to 180 degrees, equivalent to no stimulated echo correction (Units: degrees). (type: Float64) Additional save options: --SaveDecayCurve include a 4D array of the time domain decay curves resulting from the NNLS fits in the output maps dictionary --SaveNNLSBasis include a 5D (or 2D if --SetFlipAngle is used) array of NNLS basis matrices in the output maps dictionary. Note: this 5D array is extremely large for typical image sizes; in most cases, this flag should only be set when debugging small datasets --SaveRegParam include 3D arrays of the regularization parameters and resulting chi^2-factors in the output maps dictionary --SaveResidualNorm include a 3D array of the l2-norms of the residuals from the NNLS fits in the output maps dictionary BET arguments: --bet use the BET brain extraction tool from the FSL library of analyis tools to automatically create a binary brain mask. Only voxels within the binary mask will be analyzed. Note that if a mask is passed explicitly with the --mask flag, this mask will be used and the --bet flag will be ignored --betargs BETARGS BET command line interface arguments. Must be passed as a single string with arguments separated by spaces, e.g. '-m -n'. The flag '-m' indicates that a binary mask should be computed, and therefore will be added to the list of arguments if not provided (default: "-m -n -f 0.25 -R") --betpath BETPATH path to BET executable. (default: "bet")
If desired, the $T_2$-distribution computation and the $T_2$-parts analysis may be performed separately:
- When the
--T2map
flag is passed, or both--T2map
and--T2part
flags are passed, input image arrays should be 4D with data as (row, column, slice, echo) - When only the
--T2part
flag is passed, input image arrays should be 4D with data as (row, column, slice, $T_2$ bin)
Outputs
DECAES will produce up to five output files, each with the input filename (without suffix) used as a prefix. For example, if the input file is called image.nii
, the possible output files are:
image.t2dist.mat
: MATLAB file containing the 4D array of $T_2$-distributions (produced when--T2map
flag is passed)image.t2maps.mat
: MATLAB file containing $T_2$-distribution property maps and NNLS fit parameters; seeT2mapSEcorr
(produced when--T2map
flag is passed)image.t2parts.mat
: MATLAB file containing $T_2$-parts analysis results such as the MWF; seeT2partSEcorr
(produced when--T2part
flag is passed)image.log
: Log file containing the console outputimage.settings.txt
: Copy of settings file which was namedsettings.txt
(produced when passing settings as a file)
If the --dry
flag is passed, none of the above files will be produced.
Multithreading
Multithreaded parallel processing can be enabled by setting the julia
command line flag --threads
, where --threads N
enables parallel processing with N
threads:
$ julia --threads 1 decaes.jl -- image.nii <COMMAND LINE ARGS>
This is highly recommended to speed up computation time, but is not strictly required.
Examples
Default options
Suppose you have a multi spin-echo image file image.nii
which you would like to perform $T_2$ analysis on. We can call T2mapSEcorr
and T2partSEcorr
on the file image.nii
using decaes.jl
. We pass the required arguments with the appropriate flags and leave the remaining parameters at default values:
$ julia --threads 1 decaes.jl -- image.nii --T2map --T2part --TE 10e-3 --nT2 40 --T2Range 10e-3 2.0 --SPWin 10e-3 40e-3 --MPWin 40e-3 200.0e-3 --Reg lcurve
After a few seconds, the script should begin running with the following messages appearing as the script progresses (note that real images will take longer to process than this toy example):
* Starting DECAES with 1 threads * Loading input file: image.nii.gz ... * Done (0.03 seconds) * Running T2mapSEcorr on file: image.nii.gz ... T2-distribution analysis settings: Chi2Factor : nothing legacy : false MatrixSize : (100, 100, 1) MinRefAngle : 50.0 nRefAngles : 32 nRefAnglesMin : 5 nT2 : 40 nTE : 32 RefConAngle : 180.0 Reg : lcurve SaveDecayCurve : false SaveNNLSBasis : false SaveRegParam : false SaveResidualNorm : false SetFlipAngle : nothing Silent : false T1 : 1.0 T2Range : (0.01, 2.0) TE : 0.01 Threshold : 0.0 Computing T2-Distribution: 10%[==> ] ETA: 0:01:15 Computing T2-Distribution: 20%[====> ] ETA: 0:01:06 Computing T2-Distribution: 30%[=======> ] ETA: 0:00:58 Computing T2-Distribution: 40%[=========> ] ETA: 0:00:50 Computing T2-Distribution: 50%[============> ] ETA: 0:00:41 Computing T2-Distribution: 60%[==============> ] ETA: 0:00:33 Computing T2-Distribution: 70%[================> ] ETA: 0:00:25 Computing T2-Distribution: 80%[===================> ] ETA: 0:00:17 Computing T2-Distribution: 90%[=====================> ] ETA: 0:00:08 Computing T2-Distribution: 100%[========================] Time: 0:01:20 * Done (81.06 seconds) * Saving T2 distribution to file: image.t2dist.mat ... * Done (0.39 seconds) * Saving T2 parameter maps to file: image.t2maps.mat ... * Done (0.18 seconds) * Running T2partSEcorr ... T2-parts analysis settings: legacy : false MatrixSize : (100, 100, 1) MPWin : (0.04, 0.2) nT2 : 40 Sigmoid : nothing Silent : false SPWin : (0.01, 0.04) T2Range : (0.01, 2.0) * Done (0.04 seconds) * Saving T2 parts maps to file: image.t2parts.mat ... * Done (0.0 seconds) * Finished (81.75 seconds)
Settings files
As there are several required parameters, it is convenient to store settings for DECAES in a settings file. Using the same options from the previous section, we create a file settings.txt
with the following contents:
/path/to/image.nii
--T2map
--T2part
--TE
10e-3
--nT2
40
--T2Range
10e-3
2.0
--SPWin
10e-3
40e-3
--MPWin
40e-3
200.0e-3
--Reg
lcurve
If this file is located at /path/to/settings.txt
, simply prefix the filepath with the @
character to have the file contents read into the main
function:
$ julia --threads 1 decaes.jl -- @/path/to/settings.txt
- The use of settings files is highly recommended for both reproducibility and for self-documentation. The input settings file will be automatically copied into the output folder for each processed image, with the image filename prepended. In this case, for example, the copied settings file would be called
image.settings.txt
- Only one flag or value is allowed per line within a settings file. Flags which require multiple inputs (e.g.
--T2Range
above) must use one line for each input - The extension of the settings file is ignored;
.txt
is arbitrary in this example - Though not strictly necessary, using full input- and output paths is recommended. This way, one doesn't rely on relative paths and can e.g. call
julia /path/to/decaes.jl @/path/to/settings.txt
from any directory
Default settings files
Suppose you have a default settings file default.txt
, similar to the settings.txt
file in the above section. Settings in default.txt
can be individually overridden. For example, if we are interested in changing the number of $T_2$ bins nT2
to 60, but leaving all other parameters the same, run the following:
$ julia --threads 1 decaes.jl -- @/path/to/default.txt --nT2 60
Multiple input files
Multiple input files (possibly of different file types) can be passed in the obvious way:
$ julia --threads 1 decaes.jl -- image1.nii image2.mat image3.nii.gz image4.par <COMMAND LINE ARGS>
Equivalently, place multiple image paths at the top of your settings file, with each path on a new line.
Specify output folder
By default, output files are saved in the same location as the corresponding input file. If you'd like to save them in a different folder, you can use the -o
or --output
flag:
$ julia --threads 1 decaes.jl -- image.nii --output /path/to/output/folder/ <COMMAND LINE ARGS>
The requested output folder will be created if it does not already exist.
Equivalently, add --output
and /path/to/output/folder/
as consecutive lines in your settings file.
Passing image masks
Image masks can be passed into DECAES using the -m
or --mask
flag:
$ julia --threads 1 decaes.jl -- image.nii --mask /path/to/mask.nii <COMMAND LINE ARGS>
The mask file is loaded and applied to the input image via elementwise multiplication over the spatial dimensions, e.g. the mask is applied to each echo of a 4D multi-echo input image.
If multiple image files are passed, multiple corresponding mask files can be passed, too:
$ julia --threads 1 decaes.jl -- image1.nii image2.mat --mask /path/to/mask1.mat /path/to/mask2.nii.gz <COMMAND LINE ARGS>
Equivalently, add --mask
, /path/to/mask1.mat
, /path/to/mask2.mat
, ... as consecutive lines in your settings file.
If input images have been manually masked such that they are zero outside regions of interest, a mask need not be passed. The --Threshold
parameter of T2mapSEcorr
controls a first echo intensity cutoff threshold (default value 0.0), below which voxels are automatically skipped during processing
Automatic brain masking with BET
The BET brain extraction tool from the FSL library of analysis tools can be used to automatically generate a brain mask prior to analysis. Only voxels within the generated brain mask will be processed, greatly reducing analysis time. To use BET, pass the --bet
flag:
$ julia --threads 1 decaes.jl -- image.nii --bet <COMMAND LINE ARGS>
If bet
is not on your system path, you can pass the path to the bet
binary with the --betpath
flag. Additionally, you can pass arguments to bet
with the --betargs
flag:
$ julia --threads 1 decaes.jl -- image.nii --bet --betpath /path/to/bet --betargs '-m -n' <COMMAND LINE ARGS>
Note that bet
arguments must be passed as a single string to --betargs
, separated by spaces, as shown above.
Equivalently, add --bet
, --betpath
, /path/to/bet
, --betargs
, -m -n ...
as consecutive lines in your settings file.
If a mask file is passed using the --mask
flag, the --bet
flag will be ignored and the mask file will be used
Legacy options
During the port from MATLAB to Julia, some algorithms were improved using computationally more efficient algorithms, and some default parameters were modified or removed as well. This may cause small differences in output parameter maps. As an example, the flip angle optimization procedure requires finding the root of a cubic spline. In MATLAB this was performed by evaluating the spline on a very fine mesh and choosing the value nearest zero. During profiling it was found that this was a time consuming operation, and therefore in Julia this was replaced by an efficient rootfinding method tailored for cubic splines.
The differences due to algorithmic changes like the one above are quite small. For example, most tests in the DECAES test suite will pass when using a relative tolerance of $10^{-3}$, and almost all tests pass with a relative tolerance of $10^{-2}$. That is to say that nearly all outputs are identical to 3 or more significant digits, which includes $T_2$-distributions, MWF maps, etc. It should be emphasized, though, that as these differences arise from improved algorithms, any discrepencies are merely small improvements.
The --legacy
flag is available if exact reproducibility is required compared to the MATLAB version. This will ensure that all outputs match to nearly machine precision (a relative tolerance of $10^{-10}$ is used during testing). Note however that the --legacy
flag may cause a significant slowdown in processing time due to less efficient algorithms being used internally, and is therefore not recommended unless absolutely necessary. Differences due to changes in default parameters can always be overridden by passing in the desired value explicitly (e.g. --SPWin 0.014 0.040
) without the need for the --legacy
flag.