Declaration of a function



Hey,

i'am a student and I recently startetd programming with the open source library openCV and now I got to a piece of code which I just don't understand. The code which is shown below is from the official webside of openCV.
In detail i´m struggling with the declaration of this function.


1
2
3
4
5
6
7
8
  static void CannyThreshold(int, void*)
{
    blur( src_gray, detected_edges, Size(3,3) );
    Canny( detected_edges, detected_edges, lowThreshold, lowThreshold*ratio, kernel_size );
    dst = Scalar::all(0);
    src.copyTo( dst, detected_edges);
    imshow( window_name, dst );
}



I just don´t get why this funcion is initialized with an integer an a void pointer. It doesn't make any sense to me that you can´t use these parameters, because according to this code, they are declared but only without a name.
That brings me to the question why there are Parameters given to the function if you can´t use them.
The whole code is shown below:



1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
  #include "opencv2/imgproc.hpp"
#include "opencv2/highgui.hpp"
#include <iostream>
using namespace cv;
Mat src, src_gray;
Mat dst, detected_edges;
int lowThreshold = 0;
const int max_lowThreshold = 100;
const int ratio = 3;
const int kernel_size = 3;
const char* window_name = "Edge Map";
static void CannyThreshold(int, void*)
{
    blur( src_gray, detected_edges, Size(3,3) );
    Canny( detected_edges, detected_edges, lowThreshold, lowThreshold*ratio, kernel_size );
    dst = Scalar::all(0);
    src.copyTo( dst, detected_edges);
    imshow( window_name, dst );
}

int main( int argc, char** argv )
{
  CommandLineParser parser( argc, argv, "{@input | ../data/fruits.jpg | input image}" );
  src = imread( parser.get<String>( "@input" ), IMREAD_COLOR ); // Load an image
  if( src.empty() )
  {
    std::cout << "Could not open or find the image!\n" << std::endl;
    std::cout << "Usage: " << argv[0] << " <Input image>" << std::endl;
    return -1;
  }
  dst.create( src.size(), src.type() );
  cvtColor( src, src_gray, COLOR_BGR2GRAY );
  namedWindow( window_name, WINDOW_AUTOSIZE );
  createTrackbar( "Min Threshold:", window_name, &lowThreshold, max_lowThreshold, CannyThreshold );
  CannyThreshold(0, 0);
  waitKey(0);
  return 0;
}
The function that you pass to createTrackbar must be a function with return type void that takes an int and a void* as arguments. In the example above the function has no use for the parameters so there is no point in giving them names. This is a relatively common practice.

https://github.com/isocpp/CppCoreGuidelines/blob/master/CppCoreGuidelines.md#f9-unused-parameters-should-be-unnamed
Last edited on
Okay,

thank you for your quick reply. I read the link you posted a couple of hours ago.
However I still don´t get why parameters have to be passed to the function if they are not actively used.

As far as i can see this, the function works like a callback-function.

Is there any connection to this fact?


yes, it's a callback, but if you dont declare those parameters then your function prototype will not be the same as the one declared for the last parameter of createTrackbar() and a compile error will ensue.

so even though your particular callback handler makes no use of the parameters it must respect their presence because the caller will pass them regardless and the compiler is expecting them and creating space on the stack for them.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
void foo( int x ) {
  // use x
}

void bar() {
  // something
}

void gaz( int ) {
  // something
}

int main() {
  foo( 42 ); // ok
  bar( 42 ); // error, there is no bar(int)
  gaz( 42 ); // ok
}

This main() calls everything with an argument, just like the createTrackbar() calls the function that it takes as parameter (with two arguments).

The signature of foo() and gaz() does fit the usage, even though the gaz() just pretends to listen its wife. The bar() does not, and causes thus a syntax error.
Topic archived. No new replies allowed.