2014-02-13 3 views
1

Я пытаюсь выполнить реализацию алгоритма dekker для домашней работы, я понимаю концепцию, но я не могу выполнять два потока параллельно с помощью C++ 0x.Запуск потоков параллельно в C++

#include <thread> 
#include <iostream> 

using namespace std; 

class Homework2 { 

public: 
    void run() { 
     try { 
      thread c1(&Homework2::output_one, this); 

      thread c2(&Homework2::output_two, this); 


     } catch(int e) { 
      cout << e << endl; 
     } 

    } 

    void output_one() { 
     //cout << "output one" << endl; 
    } 

    void output_two() { 
     //cout << "output two" << endl; 
    } 


}; 

int main() { 
    try { 
     Homework2 p2; 
     p2.run(); 
    } catch(int e) { 
     cout << e << endl; 
    } 
    return 0; 
} 

Моя проблема заключается в том, что нити не будут возвращать эту ошибку:

terminate called without an active exception 
Aborted 

Единственный путь к успеху до сих пор для меня было добавление c1.join(); c2.join(); или .detach(); проблема в том, что join(); будет ждать окончания потоков и отделить(); ... хорошо Im не уверен, что отсоединяет, потому что нет ошибки, но также нет вывода, я думаю, что он оставляет потоки самостоятельно ...

Итак, все это сказать: Кто-нибудь знает, как я могу это сделать это оба потока для параллельного и не секвенциального? Помощь должна быть оценена!

Thanks.-

P.S: вот что я могу сделать для сборки:

g++ -o output/Practica2.out main.cpp -pthread -std=c++11 
+0

здесь является то, что я могу сделать для сборки: г ++ -o выход/Practica2.out main.cpp -pthread -std = C++ 11 – RicardoE

+0

Дон» t добавьте дополнительную информацию в комментарии. Вместо этого, [править исходный вопрос] (http://stackoverflow.com/posts/21744657/edit), чтобы включить (правильно отформатированную) информацию. –

+0

: okay:: SI отредактирует сообщение ... – RicardoE

ответ

2

Единственный путь к успеху до сих пор для меня добавлял c1.join(); c2.join(); или .detach(); ...

После того, как вы породил 2 нити, ваш основной поток продолжается, и на основе кода, заканчивается «довольно» быстро (p2.run() то return 0; относительно близки в инструкции процессора ' время'). В зависимости от того, как быстро начались потоки, у них, возможно, не хватило времени процессора, чтобы полностью «запустить» до того, как программа завершится, или если они полностью появятся, возможно, не было достаточно времени для правильной очистки ядра. Это также известно как race condition.

Вызов join на порожденных нитях из нити, из которой вы их породили, позволяет потокам закончить и правильно очистить (под капотом), прежде чем ваша программа выйдет (хорошая вещь). Вызов detach также работает в этом сценарии, так как он освобождает все ресурсы (под капотом) от вашего объекта потока, но сохраняет поток активным. В случае вызова detach ошибок не было, поскольку объекты потока были отделены от исполняемых потоков, поэтому, когда ваша программа вышла, ядро ​​(красиво) очистило потоки для вас (или, по крайней мере, это то, что может произойти, зависит от реализации OS/компилятора и т. д.), поэтому вы не видели, чтобы ваши потоки заканчивались «uncleanly».

Итак, все это, чтобы сказать: Кто-нибудь знает, как я могу сделать это, чтобы оба потока выполнялись параллельно, а не секвенциально?

Я думаю, что у вас может быть некоторое замешательство в отношении того, как работают потоки. Ваши потоки уже работают в «параллельном» (так сказать), то есть в природе потока. В вашем коде не было ничего, что было бы «параллельным» в природе (т. Е. Параллельным вычислением данных), но ваши потоки выполняются одновременно (в то же время или «параллельно» каждому).

Если вы хотите, чтобы ваш основной поток продолжался, не помещая join в функцию run, для этого потребуется немного больше кода, чем у вас в настоящее время, и я не хочу предполагать, как будущее вашего кода должно выглядеть, но вы можно посмотреть на thesetwo вопросы относительно std::thread как члена класса (и выполняются в рамках такого).

Я надеюсь, что это может помочь.

+0

Удивительно! что-то мне :) спасибо большое, было очень ясно. – RicardoE

1

Хорошо, это немного сложнее, но я попытаюсь объяснить некоторые вещи в вашем коде.

Когда вы создаете потоки в методе run, вы хотите напечатать две вещи (представьте, что вы раскомментируете строки), но объект потока уничтожается в стеке, не вызывая метод, который их создал (запустил).

Вам действительно нужно сделать две вещи: сначала создайте потоки и держите их в рабочем состоянии (например, сделайте это как указатели), а затем вызовите метод join, чтобы освободить всю память и все необходимое, когда они будут закончены.

Вы можете хранить темы в векторном что-то вроде std::vector<std::thread*>

+0

Я видел много людей, которые хранят потоки в векторах, я думаю, это хорошая практика. Это будет иметь в виду. Наконец я понял смысл join(); – RicardoE

Смежные вопросы