Суббота , 14 декабря 2019
Главная / Студентам / ОСиС / Лекция № 14. ОРГАНИЗАЦИЯ ПРОГРАММНЫХ ПОТОКОВ

Лекция № 14. ОРГАНИЗАЦИЯ ПРОГРАММНЫХ ПОТОКОВ

Рассмотрим простейший пример, в котором необходимо подсчитать количество пробелов в текстовых файлах, имена которых должны указываться в командной строке.  

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

Приведенная ниже реализация программы решения данной задачи не является единственно возможной. В данном случае рассматривается наиболее характерный вариант. 

Основная программа запускает потоки и ждет окончания их выполнения. Мы имеем всего один вычислительный процесс, но используем мультизадачные возможности операционной системы Windows. 

Листинг 14.1. Подсчет количества пробелов в текстовых файлах 

#include <windows.h> 
#include <stdio.h> 
#include <stdlib.h> 
//Название: processFile 
//Описание: исполняемый код потока 
//Входные параметры: lpFileName – имя файла 
//Выходные параметры: нет 
DWORD processFile(LPVOID lpFileName) { 
HANDLE handle;  //дескриптор файла 
DWORD numRead, total = 0; 
char buf; 
//Запрос к ОС на открытие файла (только для чтения) 
handle = CreateFile((LPCTSTR)lpFileName, GENERIC_READ, 
FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL); 
//Цикл чтения до конца файла 
do { 
//Чтение одного символа из файла 
ReadFile(handle,(LPVOID) &buf, 1, &numRead, NULL); 
if (buf == 0x20) total++; 
} while (numRead>0); 
fprintf(stderr,»( ThreadId: %Lu), File %s, spaces = %d\n», 
GetCurrentThreadId(), lpFileName, total); 
//Закрытие файла 
CloseHandle( handle ); 
return(0); 
} 
//Название: main 
//Описание: главная программа 
//Входные параметры: список имен файлов для обработки 
//Выходные параметры: нет 
int main( int argc, char *argv[]) { 
int i; 
DWORD pid; 
HANDLE hThrd[255];    //массив ссылок на потоки 
//для всех файлов, перечисленных в командной строке 
for (i=0; i<(argc-1); i++) { 
//запуск потока – обработка одного файла 
hThrd[i]=CreateThread( NULL, 0x4000, 
(LPTHREAD_START_ROUTINE) processFile, 
(LPVOID) argv[i+1], 0, &pid); 
fprintf( stdout, «processFile started (HND=%d)\n», hThrd[i]); 
} 
//ожидание окончания выполнения всех запущенных потоков 
WaitForMultipleObjects( argc-1, hThrd, true, INFINITE); 
return(0); 
}