12 #ifndef mitkConvolutionHelper_h
13 #define mitkConvolutionHelper_h
28 namespace convolution {
36 inline itk::Array<double>
wrap1d(itk::Array<double> kernel)
38 int dim = kernel.GetNumberOfElements();
39 itk::Array<double> wrappedKernel(dim);
40 wrappedKernel.fill(0.);
41 for(
int i=0; i< dim; ++i)
43 wrappedKernel.SetElement(i, kernel.GetElement((i+(dim/2))%dim));
56 inline itk::Array<double>
zeropadding1d(itk::Array<double> unpaddedSpectrum,
int paddedDimension)
59 int initialDimension = unpaddedSpectrum.GetNumberOfElements();
61 itk::Array<double> paddedSpectrum(paddedDimension);
62 paddedSpectrum.fill(0.);
64 if(paddedDimension > initialDimension)
66 unsigned int padding = paddedDimension - initialDimension;
68 for(
int i=0; i<initialDimension ;++i)
70 paddedSpectrum.SetElement(i+padding/2, unpaddedSpectrum.GetElement(i));
73 return paddedSpectrum;
84 inline itk::Array<double>
unpadAndScale(itk::Array<double> convolutionResult,
int initialDimension)
86 int transformationDimension = convolutionResult.size();
87 unsigned int padding = transformationDimension - initialDimension;
89 itk::Array<double> scaledResult(initialDimension);
90 scaledResult.fill(0.0);
92 for(
int i = 0; i<initialDimension; ++i)
94 double value = convolutionResult(i+padding/2) / transformationDimension;
95 scaledResult.SetElement(i,value);
107 inline void prepareConvolution(
const itk::Array<double>& kernel,
const itk::Array<double>& spectrum, itk::Array<double>& preparedKernel, itk::Array<double>& preparedSpectrum ){
108 int convolutionDimensions = kernel.GetSize() + spectrum.GetSize();
113 preparedSpectrum =
zeropadding1d(spectrum,convolutionDimensions);
131 typedef itk::Array<double> ConvolutionResultType;
132 ConvolutionResultType convolution(timeGrid.GetSize());
133 convolution.fill(0.0);
136 for(
unsigned int i = 0; i< (timeGrid.GetSize()-1); ++i)
138 double dt = timeGrid(i+1) - timeGrid(i);
139 double m = (aif(i+1) - aif(i))/dt;
140 double edt = exp(-lambda *dt);
142 convolution(i+1) =edt * convolution(i)
143 + (aif(i) - m*timeGrid(i))/lambda * (1 - edt )
144 + m/(lambda * lambda) * ((lambda * timeGrid(i+1) - 1) - edt*(lambda*timeGrid(i) -1));
163 typedef itk::Array<double> ConvolutionResultType;
164 ConvolutionResultType convolution(timeGrid.GetSize());
165 convolution.fill(0.0);
168 for(
unsigned int i = 0; i< (timeGrid.GetSize()-1); ++i)
170 double dt = timeGrid(i+1) - timeGrid(i);
171 double m = (aif(i+1) - aif(i))/dt;
173 convolution(i+1) = convolution(i) + constant * (aif(i)*dt + m*timeGrid(i)*dt + m/2*(timeGrid(i+1)*timeGrid(i+1) - timeGrid(i)*timeGrid(i)));
itk::Array< double > AterialInputFunctionType
Array type for the Arterial Input Function AIF(t).
itk::Array< double > TimeGridType
Type defining the time grid used by models.
itk::Array< double > zeropadding1d(itk::Array< double > unpaddedSpectrum, int paddedDimension)
Zero-pads a 1D array to a specified size.
void prepareConvolution(const itk::Array< double > &kernel, const itk::Array< double > &spectrum, itk::Array< double > &preparedKernel, itk::Array< double > &preparedSpectrum)
Prepares two arrays for FFT-based convolution.
itk::Array< double > unpadAndScale(itk::Array< double > convolutionResult, int initialDimension)
Removes padding and scales the result after inverse FFT.
itk::Array< double > wrap1d(itk::Array< double > kernel)
Wraps (circularly shifts) a 1D convolution kernel.
Find image slices visible on a given plane.
itk::Array< double > convoluteAIFWithExponential(mitk::ModelBase::TimeGridType timeGrid, mitk::AIFBasedModelBase::AterialInputFunctionType aif, double lambda)
Convolves the AIF with an exponential residue function using an iterative formula.
itk::Array< double > convoluteAIFWithConstant(mitk::ModelBase::TimeGridType timeGrid, mitk::AIFBasedModelBase::AterialInputFunctionType aif, double constant)
Convolves the AIF with a constant value using an iterative formula.