gpt4 book ai didi

c++ - 传递函数作为参数

转载 作者:行者123 更新时间:2023-11-28 07:43:12 27 4
gpt4 key购买 nike

我正在尝试将一个函数作为参数传递给另一个函数。以下代码在没有使用类时有效,但是当我尝试使用 qt 类时,出现以下错误...

error: argument of type 'void (MainWindow::)(int, int, int, int, void*)'
does not match 'void (*)(int, int, int, int, void*)'

我的代码是

#include "mainwindow.h"
#include "ui_mainwindow.h"
#include <opencv/cv.h>
#include <opencv/cvaux.h>
#include <opencv/highgui.h>

// for filelisting
#include <stdio.h>
#include <sys/file.h>
#include<io.h>
// for fileoutput
#include <string>
#include <fstream>
#include <sstream>
#include <dirent.h>
#include <sys/types.h>
using namespace std;
MainWindow::MainWindow(QWidget *parent) :
QMainWindow(parent),
ui(new Ui::MainWindow)
{
ui->setupUi(this);
roi_x0=0;
roi_y0=0;
roi_x1=0;
roi_y1=0;
numOfRec=0;
startDraw = 0;
window_name="<SPACE>add <B>save and load next <ESC>exit";
}

MainWindow::~MainWindow()
{
delete ui;
}
string MainWindow::IntToString(int num)
{
ostringstream myStream; //creates an ostringstream object
myStream << num << flush;
/*
* outputs the number into the string stream and then flushes
* the buffer (makes sure the output is put into the stream)
*/
return(myStream.str()); //returns the string form of the stringstream object
}

void MainWindow::on_mouse(int event, int x, int y, int flag, void *param)
{
if(event==CV_EVENT_LBUTTONDOWN)
{
if(!startDraw)
{
roi_x0=x;
roi_y0=y;
startDraw = 1;
} else {
roi_x1=x;
roi_y1=y;
startDraw = 0;
}
}
if(event==CV_EVENT_MOUSEMOVE && startDraw)
{

//redraw ROI selection
image2=cvCloneImage(image);
cvRectangle(image2,cvPoint(roi_x0,roi_y0),cvPoint(x,y),CV_RGB(255,0,255),1);
cvShowImage(window_name,image2);
cvReleaseImage(&image2);
}
}

void MainWindow::on_actionMark_Faces_triggered()
{
char iKey=0;
string strPrefix;
string strPostfix;
string input_directory;
string output_file;



input_directory ="E:/My/";
output_file ="pos.txt";

/* Get a file listing of all files with in the input directory */
DIR *dir_p = opendir (input_directory.c_str());
struct dirent *dir_entry_p;

if(dir_p == NULL) {
fprintf(stderr, "Failed to open directory %s\n", input_directory.c_str());

}

fprintf(stderr, "Object Marker: Input Directory: %s Output File: %s\n", input_directory.c_str(), output_file.c_str());

// init highgui
cvAddSearchPath(input_directory);
cvNamedWindow(window_name,1);
cvSetMouseCallback(window_name,on_mouse,NULL);

fprintf(stderr, "Opening directory...");
// init output of rectangles to the info file
ofstream output(output_file.c_str());
fprintf(stderr, "done.\n");

while((dir_entry_p = readdir(dir_p)) != NULL)
{
numOfRec=0;

if(strcmp(dir_entry_p->d_name, ""))
fprintf(stderr, "Examining file %s\n", dir_entry_p->d_name);

/* TODO: Assign postfix/prefix info */
strPostfix="";
//strPrefix=input_directory;
strPrefix=input_directory+dir_entry_p->d_name;
//strPrefix+=bmp_file.name;
fprintf(stderr, "Loading image %s\n", strPrefix.c_str());

if((image=cvLoadImage(strPrefix.c_str(),1)) != 0)
{

// work on current image
do

{
cvShowImage(window_name,image);

// used cvWaitKey returns:
// <B>=66 save added rectangles and show next image
// <ESC>=27 exit program
// <Space>=32 add rectangle to current image
// any other key clears rectangle drawing only
iKey=cvWaitKey(0);
switch(iKey)
{

case 27:

cvReleaseImage(&image);
cvDestroyWindow(window_name);
return;
case 32:

numOfRec++;
printf(" %d. rect x=%d\ty=%d\tx2h=%d\ty2=%d\n",numOfRec,roi_x0,roi_y0,roi_x1,roi_y1);
//printf(" %d. rect x=%d\ty=%d\twidth=%d\theight=%d\n",numOfRec,roi_x1,roi_y1,roi_x0-roi_x1,roi_y0-roi_y1);
// currently two draw directions possible:
// from top left to bottom right or vice versa
if(roi_x0<roi_x1 && roi_y0<roi_y1)
{

printf(" %d. rect x=%d\ty=%d\twidth=%d\theight=%d\n",numOfRec,roi_x0,roi_y0,roi_x1-roi_x0,roi_y1-roi_y0);
// append rectangle coord to previous line content
strPostfix+=" "+IntToString(roi_x0)+" "+IntToString(roi_y0)+" "+IntToString(roi_x1-roi_x0)+" "+IntToString(roi_y1-roi_y0);

}
else
//(roi_x0>roi_x1 && roi_y0>roi_y1)
{
printf(" hello line no 154\n");
printf(" %d. rect x=%d\ty=%d\twidth=%d\theight=%d\n",numOfRec,roi_x1,roi_y1,roi_x0-roi_x1,roi_y0-roi_y1);
// append rectangle coord to previous line content
strPostfix+=" "+IntToString(roi_x1)+" "+IntToString(roi_y1)+" "+IntToString(roi_x0-roi_x1)+" "+IntToString (roi_y0-roi_y1);
}

break;
}
}
while(iKey!='b');

{
// save to info file as later used for HaarTraining:
// <rel_path>\bmp_file.name numOfRec x0 y0 width0 height0 x1 y1 width1 height1...
if(numOfRec>0&&iKey=='b')
{
//append line
/* TODO: Store output information. */
output << strPrefix << " "<< numOfRec << strPostfix <<"\n";

cvReleaseImage(&image);
}

else
{
fprintf(stderr, "Failed to load image, %s\n", strPrefix.c_str());
}
}

}}

output.close();
cvDestroyWindow(window_name);
closedir(dir_p);
}

错误发生在行

 cvSetMouseCallback(window_name,on_mouse,NULL);

最佳答案

成员函数不同于常规函数(因为它们必须传入一个额外的隐藏“this”参数)。

这就是为什么它说:

void (MainWindow::)(int, int, int, int, void*)

不匹配:

void ()(int, int, int, int, void*)

MainWindow:: 部分很重要。

如果您使用的是 C++11,则可以使用 std::function 和 std::bind 并且它会起作用(参见 this question )。静态成员函数也可以工作,因为静态成员函数也没有 this 指针,并且表现得像常规函数(但在命名空间中,并且具有私有(private)成员访问权限)。

关于c++ - 传递函数作为参数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15417490/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com