【问题标题】:Getting error when using pthread_create [duplicate]使用 pthread_create 时出错 [重复]
【发布时间】:2012-10-29 19:41:25
【问题描述】:

可能重复:
pthread Function from a Class

我对 c++ 还很陌生,我正在做一个关于 TCP 的项目。

我需要创建一个线程,所以我用谷歌搜索并找到了这个。 http://www.yolinux.com/TUTORIALS/LinuxTutorialPosixThreads.html

我遵循它的语法但遇到错误: 'void* (ns3::TcpSocketBase::)()' 类型的参数不匹配'void* ()(void)'

代码:

tcp-socket-base.h:
class TcpSocketBase : public TcpSocket
{
 public:
 ...
 void *threadfunction();
 ....
}




tcp-socket-base.cc:

void
*TcpSocketBase::threadfunction()
{
//do something
}



..//the thread was create and the function is called here
pthread_t t1;
int temp  =  pthread_create(&t1, NULL, ReceivedSpecialAck, NULL); //The error happens here
return;
...

任何帮助将不胜感激。谢谢!

编辑:

我接受了建议,并将线程函数设为非成员函数。

namespaceXXX{

void *threadfunction()


int result  =  pthread_create(&t1, NULL, threadfunction, NULL);
      NS_LOG_LOGIC ("TcpSocketBase " << this << " Create Thread returned result: " << result );

void *threadfunction()
{
 .....
}


}

但我得到了这个错误:

初始化“int pthread_create(pthread_t*, const pthread_attr_t*, void* ()(void), void*)”的参数 3 [-fpermissive]

【问题讨论】:

  • 另外,考虑改用 boost::thread - 它会让你的生活更轻松。

标签: c++


【解决方案1】:

如果您想继续使用 pthreads,一个简单的例子是:

#include <cstdio>
#include <string>
#include <iostream>

#include <pthread.h>

void* print(void* data)
{
    std::cout << *((std::string*)data) << "\n";
    return NULL; // We could return data here if we wanted to
}

int main()
{
    std::string message = "Hello, pthreads!";
    pthread_t threadHandle;
    pthread_create(&threadHandle, NULL, &print, &message);
    // Wait for the thread to finish, then exit
    pthread_join(threadHandle, NULL);
    return 0;
}

如果可以的话,更好的选择是使用新的 C++11 thread library。它是一个更简单的 RAII 接口,它使用模板,因此您可以将任何函数传递给线程,包括类成员函数(参见 this thread)。

那么,上面的例子就简化为:

#include <cstdio>
#include <string>
#include <iostream>

#include <thread>

void print(std::string message)
{
    std::cout << message << "\n";
}

int main()
{
    std::string message = "Hello, C++11 threads!";
    std::thread t(&print, message);
    t.join();
    return 0;
}

请注意如何直接将数据传入 - 不需要与 void* 之间的强制转换。

【讨论】:

  • 感谢您的帮助。但是我得到了这个错误:从'void()()'到'void)(void)'的无效转换[-fpermissive]
  • 我修复了我的示例,以便它可以编译。传递给 pthread_create 的函数将 void 指针作为参数,允许您将数据传递到线程中。
  • 不应该是 (void *date) 吗?
  • 我将其更改为 (void *date),但转换时仍然出错。错误:void ()(void)' 到 ‘void* ()(void)。所以我在threadfunction的实现和原型前面加上'*'。这个错误消失了,但是我得到了另一个错误:在返回非void [-Werror=return-type]的函数中没有返回语句
  • void* datavoid *datavoid*data 都是同一个编译器。 C 和 C++ 通常会忽略空格。 data 是一个空指针——也就是说,它可以指向任何东西,可以是整数、浮点变量,甚至是结构或类。要使用它,请将其转换回正确的指针类型并取消引用它。
【解决方案2】:

您希望将一个类的成员函数传递给您的pthread_create 函数。线程函数应该是具有以下签名的非成员函数

void *thread_function( void *ptr );

【讨论】:

  • 这是否意味着我不应该在我的头文件中声明线程函数?
  • 没错。在您正在学习的教程中,您可以看到一个使用不是成员函数的函数的示例。成员函数需要一个类的实例来调用它(除非它是静态成员函数)。尝试使用不是类成员函数的独立函数。请参阅您问题的 cmets 中重复问题的链接
  • 如果我的线程函数需要从类中调用一些函数会怎样?
  • 您可以通过pthread_create 中的void *arg 参数将项目传递给您的线程函数。您可以使用它来传递指向您的类实例的指针
  • 但是线程函数会有一个循环调用一个成员函数每隔几秒检查一次它的值。这还能用吗?
【解决方案3】:

如果你将函数声明为静态,它将编译。

【讨论】:

    猜你喜欢
    • 2015-05-31
    • 2014-04-17
    • 2021-01-26
    • 2011-08-02
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-05-13
    • 2018-11-28
    相关资源
    最近更新 更多