C++ Don';将void*强制转换为模板化类型时,您不知道模板参数类型

C++ Don';将void*强制转换为模板化类型时,您不知道模板参数类型,c++,templates,generics,C++,Templates,Generics,我正在使用pthreads库,当我创建一个线程时,我给它一个指向模板类型对象的指针 我对模板没有经验(今天才读到),需要将pthread运行的方法声明中的void*参数强制转换为模板类型,以便访问其成员。简言之,看起来是这样的: 简言之: template <typename T> class A { ... ... ... void aMember() { ... } }; int main() { A<int> a;

我正在使用pthreads库,当我创建一个线程时,我给它一个指向模板类型对象的指针

我对模板没有经验(今天才读到),需要将pthread运行的方法声明中的void*参数强制转换为模板类型,以便访问其成员。简言之,看起来是这样的:

简言之:

template <typename T>
class A {
    ...
    ...
    ...
    void aMember() { ... }
};

int main() {
    A<int> a;

    pthread_create(..., ..., &run, &a);

    ...
    ...
    ...
}

void *run(void *arg) {
    (A*)arg->aMember()
}
模板
甲级{
...
...
...
void aMember(){…}
};
int main(){
A A;
pthread_create(…,…,&run,&a);
...
...
...
}
void*run(void*arg){
(A*)arg->aMember()
}
我的问题是我得到了所有这些错误,我不知道如何纠正。我确实理解错误,但不知道解决方法。以下是错误:

错误:前应为主表达式(标记 错误:在*标记之前缺少模板参数 错误:主表达式应在标记之前 错误:“信息”之前应为“)”

我只是不明白,当我在线程中对A进行一次转换时,我怎么可能知道它的参数类型

<>我使用C++模板:完整的指南书作为参考/学习资源,必须说我对所有需要充分理解模板的信息都感到厌倦了。我想知道是否有人能解决这个问题,或者能为我指出另一个可能提供答案的资源的方向

一如既往,我非常感谢你的帮助

编辑/更新

似乎为我的问题添加上下文可能会有所帮助。或者,可能有人可以使用不同的设计提供不同的解决方案

我使用libcurl发出HTTP请求,并根据收到的响应创建特定类型的对象(因此是模板)。我为我想发出的每个请求创建一个新线程,以便所有内容都异步运行

模板
template<typename T>
void *run(void *arg) {
    static_cast<A<T>*>(arg)->aMember();
}

int main() {
    A<int> a;

    pthread_create(..., ..., &run<int>, &a);

    ...
    ...
    ...
}
void*run(void*arg){ 静态_cast(arg)->aMember(); } int main(){ A A; pthread_create(…,…,&run,&a); ... ... ... }
与原始代码片段一样,这依赖于外部“C++”调用约定,与pthread库使用的调用约定相同。我不确定POSIX是否有任何相同的要求,但如果它们不同,那你就倒霉了,因为你不能给函数模板C语言链接

模板
void*run(void*arg){
静态_cast(arg)->aMember();
}
int main(){
A A;
pthread_create(…,…,&run,&a);
...
...
...
}

与原始代码片段一样,这依赖于外部“C++”调用约定,与pthread库使用的调用约定相同。我不确定POSIX是否有任何相同的要求,但如果它们不同,那你就倒霉了,因为你不能给函数模板C语言链接

类模板不是类,它们在给定模板参数时生成类。同样地,在你提供饼干面团之前,你不能用饼干切割器制作饼干。对
A
进行强制转换是毫无意义的

很难说什么是正确的解决方案。如果
run
只适用于一种类型,那么您知道模板参数将始终相同;您可以这样做:

void *run(void *arg) {
    A<int>* a = static_cast<A<int>*>(arg);
    a->aMember();
}
如果
run
需要在任何类型上统一操作,这是不可能的。但是,您可以考虑通用类型独立接口,并参考非模板库:

class-ABase{
公众:
//无论模板参数如何,功能都存在
虚拟void aMember()=0;
//多态基应始终具有虚拟析构函数
虚拟~ABase(){}
};
样板
甲级:公开募捐{
公众:
void aMember(){/*使用类型信息*/}
};
void*run(void*arg){
ABase*a=静态施法(arg);
a->aMember();//动态分派
}

类模板不是类,它们在给定模板参数时生成类。同样地,在你提供饼干面团之前,你不能用饼干切割器制作饼干。对
A
进行强制转换是毫无意义的

很难说什么是正确的解决方案。如果
run
只适用于一种类型,那么您知道模板参数将始终相同;您可以这样做:

void *run(void *arg) {
    A<int>* a = static_cast<A<int>*>(arg);
    a->aMember();
}
如果
run
需要在任何类型上统一操作,这是不可能的。但是,您可以考虑通用类型独立接口,并参考非模板库:

class-ABase{
公众:
//无论模板参数如何,功能都存在
虚拟void aMember()=0;
//多态基应始终具有虚拟析构函数
虚拟~ABase(){}
};
样板
甲级:公开募捐{
公众:
void aMember(){/*使用类型信息*/}
};
void*run(void*arg){
ABase*a=静态施法(arg);
a->aMember();//动态分派
}

我想我遇到了你提到的链接问题,因为它在pthread_create中表示未定义对void*MyClass::run(void*)的引用。当我显然使用@Chris调用run时,当你说
&run
,你需要在范围内定义
run
。太棒了,当我在pthread函数helpers中遇到对象类型转换的相同问题时,我希望我找到了这个线程。但有一个问题是,你能将模板传递到pthread_create吗?我想我遇到了你提到的链接问题,因为在pthread_create中,它表示未定义对void*MyClass::run(void*)的引用。当我显然使用@Chris调用run时,当你说
&run
,你需要在范围内定义
run
。太棒了,当我在pthread函数helpers中遇到对象类型转换的相同问题时,我希望我找到了这个线程。但有一个问题是,您是否能够将模板传递到pthread_create?对不起。我应该在前面为我的问题添加上下文,但我使用
class ABase {
public:
    // functionality present regardless of template argument
    virtual void aMember() = 0;

    // polymorphic bases should always have virtual destructors
    virtual ~ABase() {}
};

template <typename T>
class A : public ABase {
public:
    void aMember() { /* use type information */ }
};

void *run(void *arg) {
    ABase* a = static_cast<ABase*>(arg);
    a->aMember(); // dynamic dispatch
}