Confused with namespaces and templates

I am using the DIPlib code obtained from https://github.com/DIPlib/diplib

I have a simple program using code from it:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
#include <iostream>
#include "diplib.h"
#include "diplib/analysis.h"
#include "diplib/testing.h"
#include <opencv2/opencv.hpp>
#include "dip_opencv_interface.h"
namespace dcv = dip_opencv;

int main()
{
   cv::Mat input0 = cv::imread("input.bmp");
   cv::cvtColor(input0, input0, cv::COLOR_BGR2GRAY);
   dip::Image input = dcv::MatToDip(input0);

   dip::Image im1 = input.At(dip::Range{1}, dip::Range{1,5}) / 255.0;
   dip::Image im2 = input.At(dip::Range{2}, dip::Range{1,5}) / 255.0;

   im1.Squeeze();
   im2.Squeeze();

   auto out = dip::FindShift(im1, im2, "MTS");
   std::cout << "out: " << out << std::endl;
}


It displays a double number, as expected. However, the type of out is a FloatArray according to the documentation at https://diplib.github.io/diplib-docs/

However, I want to convert out into a C++ double value. I see that floatarray is a DimensionArray<dip::dfloat>, but I don't see anywhere in the documentation as to how to convert that into a double. How can I do that?
Last edited on
Have you tried C++ type casting?

Maybe a static_cast<> ?

https://en.cppreference.com/w/cpp/language/static_cast
whats a dfloat?
you could do the trial by fire test, see if it works...
DimensionArray dblarray<double>; //does that work? it may. it may not.
if not, you could check the library to see if they made a dip::ddouble or the like.
If those both fail, you will have to dig deeper.
** it is entirely possible that dfloat == double. some people love to rename types. like microsoft, home of (I am not kidding) at least 50 different ways to say 'int'.

what I am saying is don't get hung up in the word 'float' being used here on their own type names. You have to dig in a little to see what it really IS. just because I can typedef unsigned long long to afloat and say afloat x = 3 does not make afloat a c++ float type.
Last edited on
Maybe a static_cast<> ?


I tried
1
2
double out_double = static_cast<double>(out);
std::cout << "out: " << out_double << std::endl;


which gives

static_cast cannot convert from dip::FloatArray to double

When I tried dynamic_cast, it said double is an invalid target type

DimensionArray dblarray<double>; //does that work? it may. it may not.


That gives the error dip::DimensionArray: use of class template requires template argument list
Last edited on
I had doubts casting would work, but now we know it doesn't. You tried the two casts I would have tried.

There is reinterpret_cast<>, but I really don't suggest using that.

I suspect you are dealing with a container, it isn't a POD double. The naming convention of the library, and the last error you posted, makes me think some form of a std::vector or array in template form.

The use of auto helps hide what the data type being returned is. The documentation sure isn't helpful either.
The data type being returned is dip::FloatArray
Is that a container? A wrapper around POD like a double? What?

The documentation wanders around, hinting it is an array. Maybe.

It wouldn't be a POD double.
yea I dislike auto. I get it, but its as bad as it is good in many places.

ok, so now you have to work at it.
you have to dig up what dfloat really is, either from docs or data mine the code.

I still suspect its already double resolution.
Last edited on
> I suspect you are dealing with a container, it isn't a POD double.
so the function returns a container that holds only one element, I wonder what kind of witchcraft we may need to do in order to extract it...

double out = dip::FindShift(im1, im2, "MTS")[0];
This took me about 2 minutes to pin down on the site.

First, the return of dip::FindShift, as mentioned in this thread, is a DimensionArray, which has an operator [], so [] is a way to find entries in that array. The first entry will be at [ 0 ], but that may be missing the point. The container (somewhat like a std::vector) has a size member, telling you how many entries were returned. The FindShift function may have more information than one floating point value can present, but even then it may be entirely valid that you have only interest in the first value.

Using the mag-glass icon (search), dfloat shows that it is merely a typedef of double.

So, when using auto out = ...., merely out[ 0 ] is the first double, but be careful. You should check, first, that the size of the container is at least 1, (out.size() > 0 ) otherwise out[ 0 ] will be a memory fault.

This is typical behavior of std::vector, and is appropriate for this container.

No casting is required, and the information was quickly accessible through the website if you use the search feature.
Last edited on
Topic archived. No new replies allowed.