1
这是我正在尝试做的“最小”非工作示例。在OpenMP减少中使用多态类型
此代码是用-fopenmp
标志编译的。
#include <omp.h>
#include <iostream>
class A {
public:
virtual void operator()() = 0 ;
void combine(const A & rhs) {
// do reduction stuff
std::cout << "Combine thread : " << omp_get_thread_num() << std::endl;
}
};
class B : public A {
public:
void operator()() {
// do some B specific stuff
std::cout << "B " ;
}
} ;
class C: public A {
public:
void operator()() {
// do some C specific stuff
std::cout << "C " ;
}
} ;
class Computer {
public:
template<typename B_or_C_type>
void compute(B_or_C_type & action) {
#pragma omp declare reduction (combine_actions : B_or_C_type : omp_out.combine(omp_in)) initializer (omp_priv(omp_orig))
#pragma omp parallel for schedule(dynamic) reduction(combine_actions : action)
for(unsigned i = 0; i < 100; ++i) {
// do long computation
action() ;
}
std::cout << std::endl;
}
} ;
class Manager {
public:
Manager(Computer * computer) : computer_(computer), action_(NULL)
{}
template<typename B_or_C_type>
void set_action(B_or_C_type * action)
{
action_ = action ;
}
void run()
{
computer_->compute(*action_) ;
}
private:
Computer * computer_ ;
A * action_ ;
} ;
int main() {
Computer computer;
B b ;
C c ;
// Not working
Manager manager(&computer) ;
manager.set_action(&b) ;
manager.run() ;
manager.set_action(&c) ;
manager.run() ;
//Working
// computer.compute(b) ;
// computer.compute(c) ;
return 0;
}
我有3种类型的类:
- 操作:
A
(基类),且B
和C
(从A
派生) - 计算机:
Bar
该实现并行使用OpenMP计算(通过compute()
函数)并执行一些操作(从B
或C
课程),致电operator()
。 - 管理器:管理启动计算并设置不同的动作。
现在我有告诉我这infortunate错误,我cannot declare variable 'omp_priv' to be of abstract type 'A'
。这很好理解。我的A
类实际上是抽象的,但我希望OpenMP能够理解,我的A * action_
属性来自Manager
类是B
或C
类型。但我怎么能这样做?
奇怪的是,这个代码的工作,如果:
- 我绕过
Manager
类(在main()
取消注释作业部)
,或者:
- 我放弃平行主义和评论线34/35(那些以
#pragma
)
但是,这些都是不可想象的选项。
感谢您的回答。