
- •Список сокращений
- •Введение
- •Концепция потоков в ос
- •Понятие потока
- •Особенности организации потоков в ос Linux
- •Системный вызов clone
- •Библиотечные вызовы
- •Управление потоками
- •Синхронизация данных
- •Упражнения
- •Подготовка
- •Работа с многопоточностью
- •Пример применения многопоточности
- •Индивидуальные задания
- •Контрольные вопросы
- •Список литературы
Пример применения многопоточности
В данном примере приводится программа, позволяющая копировать файлы и параллельно измерять скорость данной операции и выводить её результат на экран. В одном потоке происходит копирование файлов, а во втором расчет скорости передачи и вывод на экран индикатора выполнения.
#include <stdlib.h>
#include <stdio.h>
#include <pthread.h>
#include <string.h>
#include <unistd.h>
int progressbar = 0;
int newsize = 0;
pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;
int coping(char **files)
{
FILE *fin, *fout;
if ((fin = fopen(files[1], "rb")) == NULL)
exit(-1);
if ((fout = fopen(files[2], "wb")) == NULL)
exit(-1);
fseek(fin, 0, SEEK_END);
long fSize = ftell(fin);
rewind(fin);
char sym;
for (int i = 0; i < fSize; i++)
{
sym = fgetc(fin);
fputc(sym, fout);
pthread_mutex_lock(&mutex);
progressbar = (int)((i / (double)fSize) * 100);
newsize = fSize - i;
pthread_mutex_unlock(&mutex);
}
fclose(fin);
fclose(fout);
return fSize;
}
void *threadFunc(void *thread_data)
{
int temp = 0;
int tempsize1 = 0, tempsize2 = 0;
double speed;
char pb[22];
while (temp < 99)
{
pthread_mutex_lock(&mutex);
temp = progressbar;
tempsize1 = newsize;
pthread_mutex_unlock(&mutex);
usleep(1000);
pthread_mutex_lock(&mutex);
tempsize2 = newsize;
pthread_mutex_unlock(&mutex);
speed = (double)(tempsize1 - tempsize2)/(1024*1024)*1000;
printf("Speed: %lf Mb/s\n", speed);
strcpy(pb, "[");
for (int i = 0; i < temp / 5; i++)
strcat(pb, "=");
strcat(pb, ">");
for (int i = 0; i < (20 - temp / 5) - 1; i++)
strcat(pb, " ");
strcat(pb, "]");
printf("%s\n", pb);
usleep(600000);
system("clear");
}
printf("[====================]\n");
pthread_exit(0);
}
int main(int argc, char *argv[])
{
if (--argc <= 1 || argc > 2)
exit(-1);
pthread_t thread;
void *thread_data = NULL;
if (pthread_create(&thread, NULL, threadFunc, thread_data) != 0)
{
fprintf(stderr, "error: pthread_create was failed\n");
exit(-1);
}
int size = coping(argv);
if (pthread_join(thread, NULL) != 0)
{
fprintf(stderr, "error: pthread_create was failed\n");
exit(-1);
}
printf("%d bytes was copied \n", size);
return 0;
}
Для примера копирования создадим файл объемом 40 Mb. Для этого воспользуемся следующей командой:
head -c 40MB /dev/zero > testfile
Скомпилируем программу следующим образом:
gcc copyfile.c -o copyfile -lpthread
Запустим программу:
./copyfile testfile testfile_new
Убедимся, что на экране появилась скорость передачи данных и индикатор выполнения.
Speed: 12.542725 Mb/s
[=============> ]