2012-05-31 146 views
1

我正在嘗試構建一個固定數量的子樹以及固定深度的樹。我不完全瞭解openMP的基本機制。樹木施工在撥打build(root_node, 0)後開始。現在讓我們假設maxDepth被賦予一個任意數字,並且maxChildren等於n。當調用build(root_node, 0)時,會啓動n線程。我的印象是,這些n線程中的每一個都會創建n線程。但仔細觀察top發現,線程永遠不會超過n。只有當maxChildren等於或高於我擁有的核心數量時,我纔可以飽和我的核心。看起來在遞歸中的後續級別的parallel塊沒有效果,將後續使用的可用線程的數量限制爲初始調用build所需的。如何在openMP中產生線程中的子線程(C++)

它爲什麼會這樣?這個遞歸是否有任何部分?而最重要的是,我能做些什麼來補救呢?提前致謝。

void 
build(Node* pNode, unsigned int depth) 
{ 
    if (depth >= maxDepth) 
     return; 
    std::list<Node*> children; 
    std::list<Node*>::iterator it; 
    // This loop cannot be parallelized because each call to select_next_node 
    // is dependent on the previous one 
    for (unsigned i = 0; i < maxChildren; ++i) 
    { 
     Node* const p_candidate_node = select_next_node(...); 
     if (is_valid(p_candidate_node)) 
      children.push_back(p_candidate_node); 
    } 

    #pragma omp parallel private(it) 
    for (it = children.begin(); it != children.end(); ++it) 
    #pragma omp single nowait 
     build(*it, depth + 1); 
} 

回答

2

默認情況下,在幾乎所有OpenMP運行時都禁用了嵌套並行。

  • 呼叫omp_set_nested(1);
  • 設置的環境變量OMP_NESTEDTRUE

嵌套並行操作可能不是你在這種情況下,想要的東西:你應該明確地由這兩個方法之一啓用它。線程數量可能增長非常快,並消耗大量系統資源。您應該使用OpenMP任務。它們應該受到所有OpenMP 3.0兼容編譯器的支持。

+0

啓用嵌套並行確實消耗了太多的資源,我一直使用'maxDepth = 10'和'maxChildren = 2'得到「線程創建失敗:資源暫時不可用」的錯誤。再次感謝你的智慧! –

+0

有沒有一種方法可以限制可以生成的最大線程數量,而無需顯式設置環境變量? –

+1

您可以通過設置「OMP_NUM_THREADS」環境變量來指定最大線程數。它的值是逗號分隔的正數列表,它指定了每個嵌套級別使用的線程數量,例如, 'export OMP_NUM_THREADS = 4,2,2'表示在基本級別有4個線程,然後對於第一個和第二個嵌套級別最多有2個線程。 –