Initial commit

This commit is contained in:
gandc 2025-04-24 01:15:54 +03:00
commit b365b81639
Signed by: gandc
GPG Key ID: 9F77B03D43C42CB4
3 changed files with 189 additions and 0 deletions

8
CMakeLists.txt Normal file
View File

@ -0,0 +1,8 @@
cmake_minimum_required(VERSION 3.10)
project(search_barrier)
find_package(Threads REQUIRED)
link_libraries(Threads::Threads)
add_executable(task1 task1.c)
add_executable(task2 task2.c)

86
task1.c Normal file
View File

@ -0,0 +1,86 @@
#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>
typedef struct {
int thread_id;
int start, end;
int *array;
int target;
} ThreadData;
int THREAD_COUNT;
int *local_results;
int global_result = -1;
pthread_barrier_t barrier;
void *search_first(void *arg) {
ThreadData *d = (ThreadData*)arg;
int found = -1;
for (int i = d->start; i < d->end; i++) {
if (d->array[i] == d->target) {
found = i;
break;
}
}
local_results[d->thread_id] = found;
int rc = pthread_barrier_wait(&barrier);
if (rc == PTHREAD_BARRIER_SERIAL_THREAD) {
int min_idx = -1;
for (int i = 0; i < THREAD_COUNT; i++) {
if (local_results[i] != -1 &&
(min_idx == -1 || local_results[i] < min_idx)) {
min_idx = local_results[i];
}
}
global_result = min_idx;
}
return NULL;
}
int main() {
int n, target;
printf("Введите N и искомое значение: ");
if (scanf("%d %d", &n, &target) != 2) {
fprintf(stderr, "Ошибка ввода\n");
return EXIT_FAILURE;
}
int *array = malloc(n * sizeof(int));
printf("Введите %d элементов массива: ", n);
for (int i = 0; i < n; i++) scanf("%d", &array[i]);
printf("Введите число потоков: ");
scanf("%d", &THREAD_COUNT);
local_results = malloc(THREAD_COUNT * sizeof(int));
pthread_barrier_init(&barrier, NULL, THREAD_COUNT);
pthread_t threads[THREAD_COUNT];
ThreadData tdata[THREAD_COUNT];
int chunk = n / THREAD_COUNT;
for (int i = 0; i < THREAD_COUNT; i++) {
tdata[i] = (ThreadData){
.thread_id = i,
.start = i * chunk,
.end = (i == THREAD_COUNT - 1 ? n : (i+1)*chunk),
.array = array,
.target = target
};
pthread_create(&threads[i], NULL, search_first, &tdata[i]);
}
for (int i = 0; i < THREAD_COUNT; i++)
pthread_join(threads[i], NULL);
if (global_result != -1)
printf("Первое вхождение %d на индексе %d\n", target, global_result);
else
printf("Значение %d не найдено\n", target);
pthread_barrier_destroy(&barrier);
free(array);
free(local_results);
return EXIT_SUCCESS;
}

95
task2.c Normal file
View File

@ -0,0 +1,95 @@
#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>
typedef struct {
int thread_id;
int start, end;
int *array;
int target;
int *counts;
int **idxs;
} ThreadData;
int THREAD_COUNT;
pthread_barrier_t barrier;
void *search_all(void *arg) {
ThreadData *d = (ThreadData*)arg;
int local_count = 0;
int capacity = d->end - d->start;
int *local_idxs = malloc(capacity * sizeof(int));
for (int i = d->start; i < d->end; i++) {
if (d->array[i] == d->target)
local_idxs[local_count++] = i;
}
d->counts[d->thread_id] = local_count;
d->idxs[d->thread_id] = local_idxs;
int rc = pthread_barrier_wait(&barrier);
if (rc == PTHREAD_BARRIER_SERIAL_THREAD) {
// общее число вхождений
int total = 0;
for (int i = 0; i < THREAD_COUNT; i++)
total += d->counts[i];
printf("Всего найдено: %d\n", total);
if (total > 0) {
printf("Индексы (возрастание): ");
for (int i = 0; i < THREAD_COUNT; i++) {
for (int j = 0; j < d->counts[i]; j++)
printf("%d ", d->idxs[i][j]);
free(d->idxs[i]);
}
printf("\n");
}
}
return NULL;
}
int main() {
int n, target;
printf("Введите N и искомое значение: ");
if (scanf("%d %d", &n, &target) != 2) {
fprintf(stderr, "Ошибка ввода\n");
return EXIT_FAILURE;
}
int *array = malloc(n * sizeof(int));
printf("Введите %d элементов массива: ", n);
for (int i = 0; i < n; i++) scanf("%d", &array[i]);
printf("Введите число потоков: ");
scanf("%d", &THREAD_COUNT);
// структуры
int *counts = calloc(THREAD_COUNT, sizeof(int));
int **idxs = malloc(THREAD_COUNT * sizeof(int*));
pthread_barrier_init(&barrier, NULL, THREAD_COUNT);
pthread_t threads[THREAD_COUNT];
ThreadData tdata[THREAD_COUNT];
int chunk = n / THREAD_COUNT;
for (int i = 0; i < THREAD_COUNT; i++) {
tdata[i] = (ThreadData){
.thread_id = i,
.start = i*chunk,
.end = (i == THREAD_COUNT-1 ? n : (i+1)*chunk),
.array = array,
.target = target,
.counts = counts,
.idxs = idxs
};
pthread_create(&threads[i], NULL, search_all, &tdata[i]);
}
for (int i = 0; i < THREAD_COUNT; i++)
pthread_join(threads[i], NULL);
pthread_barrier_destroy(&barrier);
free(array);
free(counts);
free(idxs);
return EXIT_SUCCESS;
}