Создание эффективных WIN32-приложений с учетом специфики 64-разрядной версии Windows


Несколько полезных приемов


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

На каждый разделяемый ресурс используйте отдельную структуру CRITICAL_SECTION

Если в Вашей программе имеется несколько независимых структур данных, создавайте для каждой из них отдельный экземпляр структуры CRITICAL_SECTION, Это лучше, чем защищать все разделяемые ресурсы одной критической секцией. Посмотрите на этот фрагмент кода:

int g_nNums[100]; // один разделяемый ресурс

TCHAR g_cChars[100]; // Другой разделяемый ресурс

CRITICAL_SECTION g_cs, // защищает оба ресурса

DWORD WINAPI ThreadFunc(PVOID pvParam)
{ EnterCriticalSection(&g_cs);
for (int x = 0; x < 100: x++)
{
g_nNums[x] = 0;
g_cChars|x] - TEXT('X');
}

LeaveCriticalSection(&g_cs);
return(0);
}

Здесь создана единственная критическая секция, защищающая оба массива — g_nNums и g_cChars — в период их инициализации. Но эти массивы совершенно раз личны. И при выполнении данного цикла ни один из потоков нс получит доступ ни к одному массиву. Теперь посмотрим, что будет, если ThreadFunc реализовать так:

DWORD WINAPI ThreadFunc(PVOID pvParam)
{
EnterCriticalSection(&g_cs);
for (int x = 0; x < 100; x++)

g_nNums[x] = 0;
for (x = 0; x < 100; x++)

g_cChars[x] = TEXT('X');
LeaveCriticalSection(&g_cs);
return(0);
}

В этом фрагменте массивы инициализируются по отдельности, и теоретически после инициализации g_nNums посторонний поток, которому нужен доступ только к первому массиву, сможет начать исполнение — пока ThreadFunc занимается вторым массивом. Увы, это невозможно: обе структуры данных защищены одной критичес кой секцией. Чтобы выйти из затруднения, создадим две критические секции:

int g_nNum[100]; // разделяемый ресурс

CRITICAL_SECTION g_csNums; // защищает g_nNums

TCHAR g_cChars[100]; // другой разделяемый ресурс




Начало  Назад  Вперед



Книжный магазин