С Новым годом! Форум программистов, компьютерный форум, киберфорум
C/C++: WinAPI
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.88/8: Рейтинг темы: голосов - 8, средняя оценка - 4.88
0 / 0 / 0
Регистрация: 29.03.2016
Сообщений: 36

Реализовать моделирование "столкновений" на примере работы с критическими секциями

08.09.2018, 15:39. Показов 1711. Ответов 8
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Здравствуйте,кто может помочь с программой,как понимаю,проблема с выводом,наспех написал,что требуется в выводе:
результат должен быть один .один поток пишет что то в А,например 10.,через 50мс считывает А число. если гонок нет то в А 10. Если гонки есть то: 2 поток записывает 15,1 поток записал 10, 2 записал 15 и если 1 поток считывает вместо 10 15-это столкновение.войти в крит сеекцию и выйти когда 1 поток уже считает 10 т.е прекратит испольховать ресурс. записывает один что то читает.Все работает,но скорее всего просто не нравится как выглядит.Напишите кто сможет помочь,договоримся в лс или вк например.
Вот код
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
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
результат должен быть один .один поток что то в А,через 50мс считывает А число. если гонок нет то в А 10 если гонки есть то 2 поток записывает 15,1 поток записал 10, 2 записал 15 и 1 поток считавает .вместо 10 15-это столкновение.войти в крит сеекцию и выйти когда 1 поток уже считает 10 т.е прекратит испольховать ресурс. записывает один что то читает.
#include <iostream>
#include <windows.h>
#include <cstdlib>
//#include "stdafx.h"
using namespace std;
 
int ARRAY=500;                      // инициализация размера массива
CRITICAL_SECTION critsect;          // создание объекта синхронизации Критическая Секция
int *Res=new int[ARRAY];            // создание массива из ARRAY переменных (из 500)
int Middle=0;                       // переменная середины, средний эл-т (сумма всех эл-тов массива, деленная на их кол-во)
 
 
DWORD ThreadFunction1(int Time)     // функция первого потока - увеличивает каждый эл-т массива на 20
{
 
    int Summ=0;                         // инициализация переменной суммы
    Sleep(Time);                        // задержка в Time миллисекунд
    EnterCriticalSection(&critsect);    // вход в критическую секцию
    for(int i=0; i<ARRAY; i++)          // увеличение каждого эл-та массива на 20
    {
        Res[i]+=20;
    }
    for(int i=0; i<ARRAY; i++)          // суммирование всех эл-тов массива
    {
        Summ+=Res[i];
    }
    Middle=Summ/ARRAY;                  // вычисление среднего эл-та
    cout<< "Summ=" << Summ<< "::"<< "Middle=" << Middle<< "-First"<< endl;  // вывод информации о сумме, среднем эл-те и номере потока
    LeaveCriticalSection(&critsect);    // выход из критической секции
    return 0;
}
 
DWORD ThreadFunction2(int Time)     // функция второго потока - делит каждый элемент массива на 2
{
    int Summ=0;                         // инициализация переменной суммы
    Sleep(Time);                        // задержка в Time миллисекунд
    EnterCriticalSection(&critsect);    // вход в критическую секцию
    for(int i=0; i<ARRAY; i++)          // деление всех эл-тов массива на 2
    {
        Res[i]/=2;
    }
    for(int i=0; i<ARRAY; i++)          // суммирование всех эл-тов массива
    {
        Summ+=Res[i];
    }
    Middle=Summ/ARRAY;                  // вычисление среднего эл-та
    cout<< "Summ=" << Summ<< "::"<< "Middle=" << Middle<< "-Second"<< endl;     // вывод информации о сумме, среднем эл-те и номере потока
    LeaveCriticalSection(&critsect);    // выход из критической секции
    return 0;
}
 
int main()
{
    LPDWORD ID1, ID2;                               // инициализация переменных: идентификаторы потоков
    int Time1=1000,Time2=1000;                      //                           время выполнения потоков 
    HANDLE hThread1, hThread2;                      //                           указатели на потоки
    InitializeCriticalSection(&critsect);           // инициализация критической секции
    for(int i=0; i<20; i++)                         // 20 повторений всей программы - просто для наглядности, чтобы увидеть разные варианты
    {
        for(int i=0; i<ARRAY; i++)                  // инициализация и переинициализация массива при каждом проходе по циклу т.к. значения элементов массива меняются потоками
        {
            Res[i]=i;
        }
        hThread1=CreateThread(NULL,0, (LPTHREAD_START_ROUTINE)ThreadFunction1, (LPVOID)Time1, 0, (LPDWORD)&ID1);        // создание потока 1
        hThread2=CreateThread(NULL,0, (LPTHREAD_START_ROUTINE)ThreadFunction2, (LPVOID)Time2, 0, (LPDWORD)&ID2);        // создание потока 2
        if(hThread1==NULL || hThread2==NULL)            // проверка на ошибки при вызове ф-й CreateThread
        {
            cout << "Error" << GetLastError() << endl;      // выводи Error и номер последней системной ошибки WINapi
            cin.get();                                      // ожидание ввода
            return 0;
        }
        WaitForSingleObject(hThread1,INFINITE);             // ожидание завершения потока 1
        WaitForSingleObject(hThread2,INFINITE);             // ожидание завершения потока 2
        cout<< "_____________________________"<< endl;                      
        Middle=0;                                           // обнуление переменной середины
    }
    cin.get();                                              // ожидание ввода
    return 0;
}
0
IT_Exp
Эксперт
34794 / 4073 / 2104
Регистрация: 17.06.2006
Сообщений: 32,602
Блог
08.09.2018, 15:39
Ответы с готовыми решениями:

Реализовать моделирование "столкновений" на примере работы с критическими секциями
Реализовать моделирование &quot;столкновений&quot; на примере работы с критическими секциями. Временные параметры модели определяются до начала...

Реализовать моделирование "столкновений" на примере работы с критическими секциями
Реализовать моделирование &quot;столкновений&quot; на примере работы с критическими секциями. Временные параметры модели определяются до начала...

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

8
2734 / 888 / 331
Регистрация: 10.02.2018
Сообщений: 2,097
09.09.2018, 09:52
Всё у вас как-то слишком сумбурно.
Задание одно - моделирование "столкновений", решение другое - исключение "столкновений".
Не понятно, что точно вам нужно и каким боком тут массив.
0
0 / 0 / 0
Регистрация: 29.03.2016
Сообщений: 36
09.09.2018, 21:52  [ТС]
просто надо наглядно показать ,что в ситуации когда присутствует критическая секция,то столкновений не наблюдается.А если ее убрать,то будут столкновения потоков.Проблема именно в реализации вывода,чтобы было наглядно показано это
0
2734 / 888 / 331
Регистрация: 10.02.2018
Сообщений: 2,097
09.09.2018, 23:15
Для наглядности можно сделать классический счётчик. Первый поток 10 миллионов раз увеличивает счётчик, второй поток 10 миллионов раз уменьшает счётчик. Если проблем не было, то должно получиться исходное число.
C++
1
2
3
4
5
6
7
8
9
10
11
volatile int cnt = 0;
void thread1()
{
  for (int i=0; i<10000000; i++)
    cnt++;
}
void thread2()
{
  for (int i=0; i<10000000; i++)
    cnt--;
}
Или можно 10 миллионов раз в одну переменную записывать и сразу считывать число характерное для потока. Если число не соответствует ожидаемому, то увеличивать счётчик ошибок потока.
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
volatile int var = 0;
volatile int cnt1 = 0;
volatile int cnt2 = 0;
void thread1()
{
  for (int i=0; i<10000000; i++)
  {
    var = 1;
    if (var != 1)
      cnt1++;
  }
}
void thread2()
{
  for (int i=0; i<10000000; i++)
  {
    var = 2;
    if (var != 2)
      cnt2++;
  }
}
Операции над элементами массива, подсчёт суммы и среднего - это немного путано.

Откуда в вашем описании появилась задержка в 50 мс? Это громадное время. Возможно, по заданию вам нужно не получение реальных "столкновений", а именно моделирование с искусственными задержками между записью и чтением. Гадать можно до бесконечности. Будет эффективнее, если вы напишите точно, что от вас требуется.
0
0 / 0 / 0
Регистрация: 29.03.2016
Сообщений: 36
10.09.2018, 23:00  [ТС]
да насчет задержки это образно,рассказали как примерно должно выглядеть,задача та же:просто создать два потока и наглядно показать ,что без критических секций будут наблюдаться столкновения этих потоков,а с ними столкновения не будут наблюдаться.
0
2734 / 888 / 331
Регистрация: 10.02.2018
Сообщений: 2,097
10.09.2018, 23:49
как вариант
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
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
#include <iostream>
#include <windows.h>
#include <cstdlib>
 
using namespace std;
 
CRITICAL_SECTION cs;                // создание объекта синхронизации Критическая Секция
volatile int val = 0;               // общая переменная
volatile int cnt1 = 0;              // счётчик ошибок первого потока
volatile int cnt2 = 0;              // счётчик ошибок второго потока
 
// небезопасные потоки
DWORD WINAPI UnsafeThread1(LPVOID)
{
    for (int i=0; i<10000000; i++)
    {
        val = 1;
        if (val != 1)
            cnt1++;
    }
    return 0;
}
DWORD WINAPI UnsafeThread2(LPVOID)
{
    for (int i=0; i<10000000; i++)
    {
        val = 2;
        if (val != 2)
            cnt2++;
    }
    return 0;
}
 
// безопасные потоки
DWORD WINAPI SafeThread1(LPVOID)
{
    for (int i=0; i<10000000; i++)
    {
        EnterCriticalSection(&cs);
        val = 1;
        if (val != 1)
            cnt1++;
        LeaveCriticalSection(&cs);
    }
    return 0;
}
DWORD WINAPI SafeThread2(LPVOID)
{
    for (int i=0; i<10000000; i++)
    {
        EnterCriticalSection(&cs);
        val = 2;
        if (val != 2)
            cnt2++;
        LeaveCriticalSection(&cs);
    }
    return 0;
}
 
int main()
{
    DWORD dwID1, dwID2;
    HANDLE hThread1, hThread2;                // указатели на потоки
    InitializeCriticalSection(&cs);           // инициализация критической секции
 
    cout << "Unsafe threads:" << endl;
    for (int i=0; i<10; i++)                   // 10 повторений всей программы - просто для наглядности, чтобы увидеть разные варианты
    {
        cnt1 = cnt2 = 0;                                    // обнуление счётчиков
 
        hThread1=CreateThread(NULL,0, (LPTHREAD_START_ROUTINE)UnsafeThread1, 0, 0, &dwID1);        // создание потока 1
        hThread2=CreateThread(NULL,0, (LPTHREAD_START_ROUTINE)UnsafeThread2, 0, 0, &dwID2);        // создание потока 2
 
        if (hThread1==NULL || hThread2==NULL)                // проверка на ошибки при вызове ф-й CreateThread
        {
            cout << "Error: " << GetLastError() << endl;    // выводи Error и номер последней системной ошибки WINapi
            cin.get();                                      // ожидание ввода
            return 0;
        }
 
        WaitForSingleObject(hThread1,INFINITE);             // ожидание завершения потока 1
        CloseHandle(hThread1);
 
        WaitForSingleObject(hThread2,INFINITE);             // ожидание завершения потока 2
        CloseHandle(hThread2);
 
        cout << i+1 << ") " << cnt1 << " / " << cnt2 << endl; // количество ошибок чтения
    }
 
    cout << endl << "Safe threads:" << endl;
    for (int i=0; i<10; i++)                   // 10 повторений всей программы - просто для наглядности, чтобы увидеть разные варианты
    {
        cnt1 = cnt2 = 0;                                    // обнуление счётчиков
 
        hThread1=CreateThread(NULL,0, (LPTHREAD_START_ROUTINE)SafeThread1, 0, 0, &dwID1);        // создание потока 1
        hThread2=CreateThread(NULL,0, (LPTHREAD_START_ROUTINE)SafeThread2, 0, 0, &dwID2);        // создание потока 2
 
        if (hThread1==NULL || hThread2==NULL)                // проверка на ошибки при вызове ф-й CreateThread
        {
            cout << "Error: " << GetLastError() << endl;    // выводи Error и номер последней системной ошибки WINapi
            cin.get();                                      // ожидание ввода
            return 0;
        }
 
        WaitForSingleObject(hThread1,INFINITE);             // ожидание завершения потока 1
        CloseHandle(hThread1);
 
        WaitForSingleObject(hThread2,INFINITE);             // ожидание завершения потока 2
        CloseHandle(hThread2);
 
        cout << i+1 << ") " << cnt1 << " / " << cnt2 << endl; // количество ошибок чтения
    }
 
    DeleteCriticalSection(&cs);
 
    cin.get();                                              // ожидание ввода
    return 0;
}
0
0 / 0 / 0
Регистрация: 29.03.2016
Сообщений: 36
11.09.2018, 00:01  [ТС]
Спасибо,попробую разобраться с этим.
0
0 / 0 / 0
Регистрация: 29.03.2016
Сообщений: 36
12.09.2018, 16:50  [ТС]
А на чем вы писали данную программу?у меня вот такая ошибка выскакивает,(прошу прощения за суперскрин)
Миниатюры
Реализовать моделирование "столкновений" на примере работы с критическими секциями  
0
0 / 0 / 0
Регистрация: 29.03.2016
Сообщений: 36
12.09.2018, 16:56  [ТС]
Все нормально ,на dev++ 5.11 работает
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
BasicMan
Эксперт
29316 / 5623 / 2384
Регистрация: 17.02.2009
Сообщений: 30,364
Блог
12.09.2018, 16:56
Помогаю со студенческими работами здесь

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

Реализовать моделирование "гонок" на примере работы с критическими секциями
Здравствуйте! Можете помочь разобраться и подправить ошибки? Отправили на переделку, но я не понял в чем она заключается... #include...

Работа с критическими секциями
Мое приложение (еще не готово) имеет ошибки (не все еще исправил)... Главные (из тех, что нашел) - две: Во-первых, имел место вызов...

Работа с критическими секциями
Пытаюсь синхронизировать 2 потока: char TempWord; FILE *in1; FILE *in2; FILE *out; DWORD WINAPI thrdOneF(PVOID pvParam) { ...

Работа с критическими секциями
Разбираюсь с потоками, пытаюсь сделать синхронизацию: #include &lt;windows.h&gt; #include &lt;stdio.h&gt; CRITICAL_SECTION cs; HANDLE hThr; ...


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

Или воспользуйтесь поиском по форуму:
9
Ответ Создать тему
Новые блоги и статьи
изучаю kubernetes
lagorue 13.01.2026
А пригодятся-ли мне знания kubernetes в России?
сукцессия микоризы: основная теория в виде двух уравнений.
anaschu 11.01.2026
https:/ / rutube. ru/ video/ 7a537f578d808e67a3c6fd818a44a5c4/
WordPad для Windows 11
Jel 10.01.2026
WordPad для Windows 11 — это приложение, которое восстанавливает классический текстовый редактор WordPad в операционной системе Windows 11. После того как Microsoft исключила WordPad из. . .
Classic Notepad for Windows 11
Jel 10.01.2026
Old Classic Notepad for Windows 11 Приложение для Windows 11, позволяющее пользователям вернуть классическую версию текстового редактора «Блокнот» из Windows 10. Программа предоставляет более. . .
Почему дизайн решает?
Neotwalker 09.01.2026
В современном мире, где конкуренция за внимание потребителя достигла пика, дизайн становится мощным инструментом для успеха бренда. Это не просто красивый внешний вид продукта или сайта — это. . .
Модель микоризы: классовый агентный подход 3
anaschu 06.01.2026
aa0a7f55b50dd51c5ec569d2d10c54f6/ O1rJuneU_ls https:/ / vkvideo. ru/ video-115721503_456239114
Owen Logic: О недопустимости использования связки «аналоговый ПИД» + RegKZR
ФедосеевПавел 06.01.2026
Owen Logic: О недопустимости использования связки «аналоговый ПИД» + RegKZR ВВЕДЕНИЕ Введу сокращения: аналоговый ПИД — ПИД регулятор с управляющим выходом в виде числа в диапазоне от 0% до. . .
Модель микоризы: классовый агентный подход 2
anaschu 06.01.2026
репозиторий https:/ / github. com/ shumilovas/ fungi ветка по-частям. коммит Create переделка под биомассу. txt вход sc, но sm считается внутри мицелия. кстати, обьем тоже должен там считаться. . . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru