Форум программистов, компьютерный форум, киберфорум
C/С++ под Linux
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.52/29: Рейтинг темы: голосов - 29, средняя оценка - 4.52
0 / 0 / 0
Регистрация: 02.11.2012
Сообщений: 33

Синхронизация потоков

05.11.2012, 19:04. Показов 5855. Ответов 18
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Программа должна работать так: один поток печатает свой id пишет время, спит 20 секунд, потом опять пишет время. После завершения работы первого потока тоже самое должен сделать второй поток. У меня проблема в том, что я не могу их разделить, по идее это должна делать функция pthread_join(), как я это понял, но ничего подобного не происходит.

Другая проблема, не могу понять какие надо использовать спецификаторы для printf что бы время и pid выводились на экран в нормальном виде, а не 8-значными отрицательными числами.

Вот мой код:
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>
#include <sys/types.h>
#include <time.h>
#include <unistd.h>
 
void *func( void *ptr );
 
main()
{
     pthread_t thread1, thread2;
     char *msg1 = "I am thread 1! Hello!";
     char *msg2 = "I am thread 2! Hello!";
     int  iret1, iret2;
 
     iret1 = pthread_create( &thread1, NULL, func, (void*) msg1);
     iret2 = pthread_create( &thread2, NULL, func, (void*) msg2);
 
     pthread_join( thread1, NULL);
     pthread_join( thread2, NULL); 
 
     printf("Thread 1 returns: %d\n",iret1);
     printf("Thread 2 returns: %d\n",iret2);
     exit(0);
}
 
void *func( void *ptr )
{
    time_t t;
        printf("%d\n", pthread_self());
    printf("%d\n", time(&t));
    sleep(20);
    printf("%d\n", time(&t));
}
0
cpp_developer
Эксперт
20123 / 5690 / 1417
Регистрация: 09.04.2010
Сообщений: 22,546
Блог
05.11.2012, 19:04
Ответы с готовыми решениями:

Синхронизация потоков
Доброго времени суток! Задача состоит в том, чтобы отсортировать слова пользуясь алгоритмом слияния. Алгоритм реализован правильно, но...

Синхронизация потоков. Нужны ли они?
Задание: Выполнить индивидуальное задание параллельным алгоритмом (обязательно использовать для разграничения общих ресурсов системные...

Синхронизация потоков с++
Реализовать модуль создающий 4 балансировочных потока обеспечивающий 100% загрузку CPU (A,B,C,D). Каждый поток должен выводить на консоль...

18
Почетный модератор
7393 / 2639 / 281
Регистрация: 29.07.2006
Сообщений: 13,696
05.11.2012, 19:12
Цитата Сообщение от _Vados Посмотреть сообщение
по идее это должна делать функция pthread_join()
Нет, эта функция просто блокирует тот, поток, который ее вызвал (в твоем случе - главный поток) до завершения работы потока переданного в параметре.
Ты вызвал pthread_create и создал два потока, они работают параллельно, а не друг за другом. Если нужно синхронизация, то используй любой механизм доступный для нее. Либо создавай второй поток, когда закончил работу первый.
0
0 / 0 / 0
Регистрация: 02.11.2012
Сообщений: 33
05.11.2012, 23:28  [ТС]
То, есть вы хотите сказать, что функция pthread_create() создает его и сразу же выполняет??

Добавлено через 13 минут
просто, как я понял, я вызываю два раза функцию pthread_create(), тем самым создаю два потока, а потом с помощью функции pthread_join() передаю управление сначала одному потоку, потом другому
0
1443 / 1326 / 131
Регистрация: 20.03.2009
Сообщений: 4,689
Записей в блоге: 11
05.11.2012, 23:36
Цитата Сообщение от _Vados Посмотреть сообщение
То, есть вы хотите сказать, что функция pthread_create() создает его и сразу же выполняет??
Сразу, не сразу, зависит от ОС и количества ядер на процессоре.
0
Почетный модератор
7393 / 2639 / 281
Регистрация: 29.07.2006
Сообщений: 13,696
05.11.2012, 23:45
Цитата Сообщение от _Vados Посмотреть сообщение
То, есть вы хотите сказать, что функция pthread_create() создает его и сразу же выполняет??
А чего нужно ждать?
Цитата Сообщение от _Vados Посмотреть сообщение
просто, как я понял, я вызываю два раза функцию pthread_create(), тем самым создаю два потока
Цитирую ман:
The pthread_create() function starts a new thread in the calling process. The
new thread starts execution by invoking start_routine(); arg is passed as the
sole argument of start_routine()
Запускает новый поток в процессе. и т. д.
Цитата Сообщение от _Vados Посмотреть сообщение
а потом с помощью функции pthread_join() передаю управление сначала одному потоку, потом другому
Ты документацию по join читал? Где там про передачу управления потокам?
http://cs.mipt.ru/docs/courses... hread4.htm
0
0 / 0 / 0
Регистрация: 02.11.2012
Сообщений: 33
06.11.2012, 02:35  [ТС]
В общем спустя пару часов я въехал, что делают эти функции, теперь пытаюсь передать из одного потока массив в другой поток, который должен его напечатать и оно у меня благополучно виснет, в чем проблема, подскажите плз.

C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>
#include <sys/types.h>
#include <time.h>
#include <unistd.h>
 
#define MAX 3
pthread_mutex_t mutex1 = PTHREAD_MUTEX_INITIALIZER;
pthread_cond_t cond = PTHREAD_COND_INITIALIZER;
 
void *func1(void* ptr);
void *func2(void *ptr);
int A[MAX];
int i;
 
main()
{
     pthread_t thread1, thread2;
     int  iret1, iret2;
 
     iret1 = pthread_create( &thread1, NULL, func1, NULL);
     iret2 = pthread_create( &thread2, NULL, func2, NULL);
 
     pthread_join( thread1, NULL);
     pthread_join( thread2, NULL); 
 
     printf("Thread 1 returns: %d\n",iret1);
     printf("Thread 2 returns: %d\n",iret2);
     exit(0);
}
 
void *func1(void *ptr)
{
    for (i=0; i < MAX; i++)
    {   
        pthread_mutex_lock( &mutex1 );
        
        A[i] = rand();
        printf("Thread 1 is ready to move ",i," element to thread 2\n");
        sleep(1);
        pthread_cond_wait( &cond, &mutex1 );
        pthread_mutex_unlock( &mutex1 );
    }
}
 
void *func2(void *ptr)
{
    for (i=0; i < MAX; i++)
    {
        pthread_mutex_lock( &mutex1 );
        printf("Thread 2 shows: ",A[i],"\n");
        sleep(1);
        pthread_cond_signal( &cond );
        pthread_mutex_unlock( &mutex1 );
    }
}
Добавлено через 4 минуты
Документацию не читал, и до вашего сообщения понятия о ней не имел.
0
1265 / 979 / 384
Регистрация: 02.09.2012
Сообщений: 3,026
06.11.2012, 17:02
А обязательно на каждом шаге блокировать? Проще нельзя

C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
void *func1(void *ptr)
{
    for (int i = 0; i < MAX; i++)
    {
        A[i] = rand();
        printf("Thread 1 is ready to move %i-element=%i to thread 2\n", i, A[i]);
        sleep(1);
    }
    pthread_cond_signal( &cond );
}
 
void *func2(void *ptr)
{
    pthread_cond_wait( &cond, &mutex1 );
    for (int i = 0; i < MAX; i++)
    {
        printf("Thread 2 shows: %i\n", A[i]);
        sleep(1);
    }
}
И кто вас так странно научил printf-ом пользоваться? надо бы тоже исправляться
1
0 / 0 / 0
Регистрация: 02.11.2012
Сообщений: 33
07.11.2012, 00:42  [ТС]
Та меня вообще не учили им пользоваться, сразу cin cout использовал с самого начала, а в линуксе оказывается по умолчанию нету хэдера iostream и с их подключением много возни... Про спецификаторы %i и %ld узнал только вчера когда код писать начал, для меня он почти что новый если можно так сказать, да как и в прочем программирование потоков...та и линукс в общем
0
1443 / 1326 / 131
Регистрация: 20.03.2009
Сообщений: 4,689
Записей в блоге: 11
07.11.2012, 07:38
Цитата Сообщение от _Vados Посмотреть сообщение
а в линуксе оказывается по умолчанию нету хэдера iostream
что-то новенькое.
0
1265 / 979 / 384
Регистрация: 02.09.2012
Сообщений: 3,026
07.11.2012, 15:48
Цитата Сообщение от _Vados Посмотреть сообщение
Та меня вообще не учили им пользоваться, сразу cin cout использовал с самого начала, а в линуксе оказывается по умолчанию нету хэдера iostream и с их подключением много возни... Про спецификаторы %i и %ld узнал только вчера когда код писать начал, для меня он почти что новый если можно так сказать, да как и в прочем программирование потоков...та и линукс в общем

Не по теме:

Понятие "научить программировать" вообще утопия ИМХО. Человека нельзя научить программировать, пока он сам не научиться... Так что толковую книжку и побольше практики-практики... руку набьете, будет легче....



Так с реализацией вашей задачки что делать будем, вопрос решен или будем на каждом шаге синхронизировать?
0
0 / 0 / 0
Регистрация: 02.11.2012
Сообщений: 33
07.11.2012, 19:34  [ТС]
Цитата Сообщение от Dmitriy_M Посмотреть сообщение
что-то новенькое.
Серьезно, я установил Ubuntu 12.04 с офф сайта, открыл gedit, начал подключать кучу файлов заголовков одним из которых был iostream, а компилятор мне как начнет ошибки выдавать мол файл не найден. А вот всякие stdio и прочее были.

Добавлено через 11 минут
Цитата Сообщение от grgdvo Посмотреть сообщение

Не по теме:

Понятие "научить программировать" вообще утопия ИМХО. Человека нельзя научить программировать, пока он сам не научиться... Так что толковую книжку и побольше практики-практики... руку набьете, будет легче....



Так с реализацией вашей задачки что делать будем, вопрос решен или будем на каждом шаге синхронизировать?
Такой вариант тоже хорош. Я вот сейчас разбираюсь с блокировкой чтения-записи разобраться и пытаюсь ее с rwlock реализовать, это один из пунктов моего задания, он же и последний. Скоро скину код.
0
Каратель
Эксперт С++
6610 / 4029 / 401
Регистрация: 26.03.2010
Сообщений: 9,273
Записей в блоге: 1
07.11.2012, 19:37
Цитата Сообщение от _Vados Посмотреть сообщение
Серьезно, я установил Ubuntu 12.04 с офф сайта, открыл gedit, начал подключать кучу файлов заголовков одним из которых был iostream, а компилятор мне как начнет ошибки выдавать мол файл не найден. А вот всякие stdio и прочее были.
sudo apt-get install g++
0
0 / 0 / 0
Регистрация: 02.11.2012
Сообщений: 33
08.11.2012, 00:48  [ТС]
Цитата Сообщение от Jupiter Посмотреть сообщение
sudo apt-get install g++
я им и компилировал
0
0 / 0 / 0
Регистрация: 02.11.2012
Сообщений: 33
14.11.2012, 23:51  [ТС]
Цитата Сообщение от _Vados Посмотреть сообщение
Серьезно, я установил Ubuntu 12.04 с офф сайта, открыл gedit, начал подключать кучу файлов заголовков одним из которых был iostream, а компилятор мне как начнет ошибки выдавать мол файл не найден. А вот всякие stdio и прочее были.

Добавлено через 11 минут


Такой вариант тоже хорош. Я вот сейчас разбираюсь с блокировкой чтения-записи разобраться и пытаюсь ее с rwlock реализовать, это один из пунктов моего задания, он же и последний. Скоро скину код.
Извиняюсь за "маленькую" задержку вот мой код с rwlock:

C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>
#include <sys/types.h>
#include <time.h>
#include <unistd.h>
 
#define MAX 10
pthread_mutex_t mutex1 = PTHREAD_MUTEX_INITIALIZER;
pthread_cond_t cond = PTHREAD_COND_INITIALIZER;
pthread_rwlock_t rwlock1 = PTHREAD_RWLOCK_INITIALIZER;
 
void *func1(void* ptr);
void *func2(void *ptr);
int A[MAX];
int i;
 
main()
{
     pthread_t thread1, thread2;
     int  iret1, iret2;
 
     iret1 = pthread_create( &thread1, NULL, func1, NULL);
     iret2 = pthread_create( &thread2, NULL, func2, NULL);
 
     pthread_join( thread1, NULL);
     pthread_join( thread2, NULL); 
 
     printf("Thread 1 returns: %d\n",iret1);
     printf("Thread 2 returns: %d\n",iret2);
     exit(0);
}
 
void *func1(void *ptr)
{
    pthread_rwlock_wrlock( &rwlock1 );
    for (int i = 0; i < MAX; i++)
    {
        A[i] = rand()%60;
        printf("Thread 1 is ready to move %i-element=%i to thread 2\n", i, A[i]);
        sleep(1);
    }
    pthread_rwlock_unlock( &rwlock1 );
//    pthread_cond_signal( &cond );
}
 
void *func2(void *ptr)
{
//    pthread_cond_wait( &cond, &mutex1 );
    pthread_rwlock_rdlock(&rwlock1 );
    for (int i = 0; i < MAX; i++)
    {
        printf("Thread 2 shows: %i\n", A[i]);
        sleep(1);
    }
    pthread_rwlock_unlock( &rwlock1 );
 
}
Работает так же, как и у товарища grgdvo, кстати, заинтересовался синхронизацией на каждом шаге, но у меня она так и не начала работать, было бы интересно глянуть на данную реализацию.
0
1265 / 979 / 384
Регистрация: 02.09.2012
Сообщений: 3,026
15.11.2012, 16:43
Что-то понравились мне события... пробую... пишу без проверки, простите, нет времени

C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
void *func1(void *ptr)
{
    for (int i = 0; i < MAX; i++)
    {
        A[i] = rand();
        printf("Thread 1 is ready to move %i-element=%i to thread 2\n", i, A[i]);
        pthread_cond_signal( &wait_next_i );
        pthread_cond_wait( &wait_continue, &mutex2 );
 
        sleep(1);
    }
}
 
void *func2(void *ptr)
{
    for (int i = 0; i < MAX; i++)
    {
        pthread_cond_wait( &wait_next_i, &mutex1 );
        printf("Thread 2 shows: %i\n", A[i]);
        pthread_cond_signal( &wait_continue );
        sleep(1);
    }
}
Думаю можно и на мьютексах изобразить, но только уже на выходных.

Кстатите не уверен, что ваша реализация с rwlock'ом правильная... Поменяйте местами запуски потоков... что-то мне подсказывает, что мусор напечатает, хотя я толком не работал с rwlock, помню только теоретически.
0
1443 / 1326 / 131
Регистрация: 20.03.2009
Сообщений: 4,689
Записей в блоге: 11
15.11.2012, 17:01
Цитата Сообщение от _Vados Посмотреть сообщение
Серьезно, я установил Ubuntu 12.04 с офф сайта, открыл gedit, начал подключать кучу файлов заголовков одним из которых был iostream, а компилятор мне как начнет ошибки выдавать мол файл не найден. А вот всякие stdio и прочее были.
Если написать что-то подобное:
C++ (Qt)
1
2
3
4
5
6
7
#include <iostream.h>
 
int main()
{
    std::cout<<"hello"<<std::endl;
    return 0;
}
то выдас
Bash
1
foo.cpp:1:22: фатальная ошибка: iostream.h: No such file or directory
Цитата Сообщение от grgdvo Посмотреть сообщение
Думаю можно и на мьютексах изобразить, но только уже на выходных.
не проще ли использовать n-арный семафор?
Писатель никогда не блокируется, а читатель не на каждом шаге блокируется.
1
1265 / 979 / 384
Регистрация: 02.09.2012
Сообщений: 3,026
15.11.2012, 17:14
не проще ли использовать n-арный семафор?
Писатель никогда не блокируется, а читатель не на каждом шаге блокируется.
Насколько я успеваю уловить ход общения выше, речь идет именно "поиграться" в синхронизацию, а не решить какую-то конкретную задачу.

Ваш вариант мне требует осмысления...! Писатель поднимает семафор на каждой итерации, а читатель при каждой следующей итерации опускает его, при нуле ждет поднятия? Я правильно уловил? Да, точно, должно работать.
0
1443 / 1326 / 131
Регистрация: 20.03.2009
Сообщений: 4,689
Записей в блоге: 11
15.11.2012, 17:31
Цитата Сообщение от grgdvo Посмотреть сообщение
Писатель поднимает семафор на каждой итерации, а читатель при каждой следующей итерации опускает его, при нуле ждет поднятия? Я правильно уловил?
Математическая модель семафора это обычный счетчик. В этой задаче семафор можно рассматривать как счетчик доступных ресурсов.
Соответственно писатель после того как записал что-то увеличивает счетчик доступных ресурсов на единицу.
Читатель уменьшает счетчик при чтение. Если счетчик равен 0, то читатель блокируется до того момента, пока состояние счетчика не измениться.
0
1259 / 650 / 44
Регистрация: 06.02.2011
Сообщений: 1,654
17.11.2012, 21:46
Цитата Сообщение от grgdvo Посмотреть сообщение
Думаю можно и на мьютексах изобразить, но только уже на выходных.
кондишены без мьютексов не работают
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
raxper
Эксперт
30234 / 6612 / 1498
Регистрация: 28.12.2010
Сообщений: 21,154
Блог
17.11.2012, 21:46
Помогаю со студенческими работами здесь

Синхронизация потоков на элементарном уровне (переключение потоков)
в общем разбираюсь с потоками, на сколько понял мне нужен lock Вот имеется просто пример public void RunAdd() ...

Синхронизация потоков: проблема гонки потоков
Есть проблема в синхронизации потоков, которую я не знаю, как решить. Точнее у меня получается типичная гонка потоков. Есть функция,...

Синхронизация потоков
Не так давно начал заниматься c#.. возникла следующее недопонимание потоков. Программа ищет в цикле случайное число от 0 до 10, цикл...

синхронизация потоков
Добрый вечер! Имеется несколько потоков, каждый поток выполняет генетический алгоритм, как их синхронизировать, чтобы в определенный момент...

Синхронизация потоков
Есть ли возможность в C# сделать часть кода потока защищенным от прерывания другими потоками. Lock не подходит, т.к. потоки не используют...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
19
Ответ Создать тему
Новые блоги и статьи
Оттенки серого
Argus19 18.03.2026
Оттенки серого Нашёл в интернете 3 прекрасных модуля: Модуль класса открытия диалога открытия/ сохранения файла на Win32 API; Модуль класса быстрого перекодирования цветного изображения в оттенки. . .
SDL3 для Desktop (MinGW): Рисуем цветные прямоугольники с помощью рисовальщика SDL3 на Си и C++
8Observer8 17.03.2026
Содержание блога Финальные проекты на Си и на C++: finish-rectangles-sdl3-c. zip finish-rectangles-sdl3-cpp. zip
Символические и жёсткие ссылки в Linux.
algri14 15.03.2026
Существует два типа ссылок — символические и жёсткие. Ссылка в Linux — это запись в каталоге, которая может указывать либо на inode «файла-ИСТОЧНИКА», тогда это будет «жёсткая ссылка» (hard link),. . .
[Owen Logic] Поддержание уровня воды в резервуаре количеством включённых насосов: моделирование и выбор регулятора
ФедосеевПавел 14.03.2026
Поддержание уровня воды в резервуаре количеством включённых насосов: моделирование и выбор регулятора ВВЕДЕНИЕ Выполняя задание на управление насосной группой заполнения резервуара,. . .
делаю науч статью по влиянию грибов на сукцессию
anaschu 13.03.2026
прикрепляю статью
SDL3 для Desktop (MinGW): Создаём пустое окно с нуля для 2D-графики на SDL3, Си и C++
8Observer8 10.03.2026
Содержание блога Финальные проекты на Си и на C++: hello-sdl3-c. zip hello-sdl3-cpp. zip Результат:
Установка CMake и MinGW 13.1 для сборки С и C++ приложений из консоли и из Qt Creator в EXE
8Observer8 10.03.2026
Содержание блога MinGW - это коллекция инструментов для сборки приложений в EXE. CMake - это система сборки приложений. Здесь описаны базовые шаги для старта программирования с помощью CMake и. . .
Как дизайн сайта влияет на конверсию: 7 решений, которые реально повышают заявки
Neotwalker 08.03.2026
Многие до сих пор воспринимают дизайн сайта как “красивую оболочку”. На практике всё иначе: дизайн напрямую влияет на то, оставит человек заявку или уйдёт через несколько секунд. Даже если у вас. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru