Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

itk::ElastixRegistrationMethod UpdateLargestPossibleRegion() APi in C++ taking more than 15 seconds to find the Coarse Edge detection for fixed and moving edge #932

Open
kyadav78 opened this issue Jul 5, 2023 · 0 comments

Comments

@kyadav78
Copy link

kyadav78 commented Jul 5, 2023

Hi All,
Below is my C++ code snippet for Coarse Edge detection after modifying the ..\elastix-5.1.0\dox\externalproject\ElastixTranslationExample.cxx project and i have found the call to UpdateLargestPossibleRegion() is taking more than 15 seconds to complete. is there any way to reduce the execution timing? Also i would like to know which are the specific library of elastix and ITK is required to link and execute it , as i had used F:\elast\elastix-5.1.0\dox\externalproject\CMakeLists.txt and it added almost all the libraries in the project file.
Please advise how to optimize my code, as i am unware about internals of the Elastix and ITK.

C++ code snippet:

constexpr unsigned int ImageDimension = 2;
using PixelType = float;
using ImageType = itk::Image<PixelType, ImageDimension>;
ImageType::Pointer itkFixedImage = ImageType::New();
ImageType::Pointer itkMovingImage = ImageType::New();
cout << "Built with OpenCV 0" << CV_VERSION << endl;
cv::Mat semimg = cv::imread("C:/Users/e182000/Downloads/FixedImage.tif", cv::IMREAD_UNCHANGED);
int isFloat = semimg.depth() ;
cv::Mat sem_input;

using BridgeType = itk::OpenCVImageBridge;
itkFixedImage = BridgeType::CVMatToITKImage< ImageType >(semimg);

cv::Mat cadimg = cv::imread("C:/Users/e182000/Downloads/MovingImage.tif",cv::IMREAD_UNCHANGED);
cv::Mat cad_input;

itkMovingImage = BridgeType::CVMatToITKImage< ImageType >(cadimg);

const auto parameterObject = elx::ParameterObject::New();
parameterObject->SetParameterMap(
elx::ParameterObject::ParameterMapType{ { "ImageSampler", { "RandomCoordinate" } },
{ "MaximumNumberOfIterations", { "400","400","1000" } },
{ "Metric", { "AdvancedMattesMutualInformation","TransformBendingEnergyPenalty" } },
{ "Optimizer", { "AdaptiveStochasticGradientDescent" } },
{"AutomaticParameterEstimation", {"true" }},
{"AutomaticTransformInitialization", {"false"}},
{"BSplineInterpolationOrder",{ "3"}},
{"CheckNumberOfSamples", {"true"}},
{"DefaultPixelValue", {"-1"}},
{"ErodeMask", {"false" }},
{"FinalBSplineInterpolationOrder", {"2"}},
{"FinalGridSpacingInPhysicalUnits", {"15","15"}},
{"FixedImageBSplineInterpolationOrder", {"2"}},
{"FixedImageDimension",{ "2"}},
{"FixedImagePyramid",{"FixedRecursiveImagePyramid"}},
{"FixedInternalImagePixelType",{"float"}},
{"GridSpacingSchedule",{"0.25", "0.5", "1"}},
{"HowToCombineTransforms", {"Compose"}},
{"ImagePyramidSchedule", {"8", "8", "4" ,"4", "1", "1"}},
// {"ImageSampler", {"RandomCoordinate"}},
{"Interpolator", {"BSplineInterpolator"}},
//{"MaximumNumberOfIterations", {"1", "1", "1"}},
{"MaximumNumberOfSamplingAttempts", {"8"}},
{"MaximumStepLength", {"8", "4", "1"}},
{"Metric0Weight",{"1"}},
{"Metric1Weight", {"12"}},
{"MinimumStepLength", {"0.25"}},
{"MovingImageDimension", {"2"}},
{"MovingImagePyramid", {"MovingRecursiveImagePyramid" }},
{"MovingInternalImagePixelType", {"float"}},
{"NewSamplesEveryIteration", {"true"}},
{"NumberOfHistogramBins", {"16"}},
{"NumberOfResolutions",{"3"}},
{"NumberOfSamplesForExactGradient", {"4096"}},
{"NumberOfSpatialSamples", {"3000"}},
{"PassiveEdgeWidth", {"1"}},
{"Registration", {"MultiMetricMultiResolutionRegistration"}},
{"ResampleInterpolator", {"FinalBSplineInterpolator"}},
{"Resampler", {"DefaultResampler"}},
{"ResultImageFormat", {"nii"}},
{"ResultImagePixelType", {"float"}},
{"UseAdaptiveStepSizes", {"true" }},
{"UseDirectionCosines", {"true" }},
{"UseMultiThreadingForMetrics", {"true"}},
{"UseRandomSampleRegion", {"false"}},
{"WriteFinalTransformParameters", {"false"}},
{"WriteIterationInfo", {"false"}},
//{"WriteResultImage", {"false"}},

                                        { "Transform", { "RecursiveBSplineTransform" } }
                                      });

const auto filter = itk::ElastixRegistrationMethod<ImageType, ImageType>::New();
if (filter.IsNull() == true || parameterObject.IsNull()==true)
{
cout << "filter failed 4->" << CV_VERSION << endl;
return EXIT_FAILURE;
}
else
{
cout << "all good till now" << endl;
}
filter->SetFixedImage(itkFixedImage);
filter->SetMovingImage(itkMovingImage);
filter->SetParameterObject(parameterObject);
auto tempFixedImg=filter->GetFixedImage();
filter->SetNumberOfThreads(12); // also try 12
filter->SetLogToConsole(false);
filter->SetLogToFile(false);
time_t start, end;
time(&start);
filter->UpdateLargestPossibleRegion();
time(&end);
double time_taken = double(end - start);
cout << "Time taken by program is : " << fixed << time_taken << setprecision(5);

Regards
Kunal

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant