Программирование на языке С. 1. Написать программу, которая считывает 3 файла (1.txt,2.txt,3.

Дата публикации: 27.01.2024

Программирование на языке С. 1. Написать программу, которая считывает 3 файла (1.txt,2.txt,3.


Программирование на языке С. 1. Написать программу, которая считывает 3 файла (1.txt,2.txt,3.

Проблема в вашей программе заключается в том, что переменные operYm, operPl, operStep, n1, n2, n3, s1, s2, s3 и result объявлены только в функции main, и они не видны в функциях потоков. Чтобы исправить это, вы можете передать эти переменные в функции потоков через аргументы.

Вот исправленный код:

#include <stdio.h>
#include <math.h>
#include <stdlib.h>
#include <pthread.h>
#include <semaphore.h>

// Объявление семафоров
sem_t sem1, sem2, sem3;

// Объявление функций потоков
void* thread1(void* arg);
void* thread2(void* arg);
void* thread3(void* arg);

int main() {
    FILE *f1, *f2, *f3, *fS;
    int n1, n2, n3, s1, s2, s3, result;
    char operYm, operPl, operStep;

    f1 = fopen("file1.txt", "r");
    f2 = fopen("file2.txt", "r");
    f3 = fopen("file3.txt", "r");
    fS = fopen("fOtvet.txt", "w");

    if (f1 == NULL || f2 == NULL || f3 == NULL || fS == NULL) {
        printf("Ошибка открытия файла");
        return 1;
    }

    // проверка символов умножения, сложения, степени
    fscanf(f1, " %c", &operYm);
    fscanf(f2, " %c", &operPl);
    fscanf(f3, " %c", &operStep);

    // считывание значений второй строки
    fscanf(f1, "%d", &n1);
    fscanf(f2, "%d", &n2);
    fscanf(f3, "%d", &n3);

    // Инициализация семафоров
    sem_init(&sem1, 0, 0);
    sem_init(&sem2, 0, 0);
    sem_init(&sem3, 0, 0);

    // Создание потоков
    pthread_t tid1, tid2, tid3;
    pthread_create(&tid1, NULL, thread1, &operYm);
    pthread_create(&tid2, NULL, thread2, &operPl);
    pthread_create(&tid3, NULL, thread3, &operStep);

    // Ожидание завершения потоков
    pthread_join(tid1, NULL);
    pthread_join(tid2, NULL);
    pthread_join(tid3, NULL);

    if (operYm == '*') {
        s1 = n1 * n2 * n3;
    }
    if (operPl == '+') {
        s2 = n1 + n2 + n3;
    }
    if (operStep == '^') {
        s3 = pow(2, n1) + pow(2, n2) + pow(2, n3);
    }

    result = s1 + s2 + s3;

    fprintf(fS, "%d|%d|%d|%d|\n", s1, s2, s3, result);

    fclose(f1);
    fclose(f2);
    fclose(f3);
    fclose(fS);

    // Удаление семафоров
    sem_destroy(&sem1);
    sem_destroy(&sem2);
    sem_destroy(&sem3);

    return 0;
}

// Поток 1
void* thread1(void* arg) {
    char operYm = *((char*) arg);
    int n1, n2, n3;
    sem_wait(&sem1); // Ожидание сигнала от главного потока
    if (operYm == '*') {
        s1 = n1 * n2 * n3;
    }
    sem_post(&sem2); // Отправка сигнала потоку 2
    pthread_exit(NULL);
}

// Поток 2
void* thread2(void* arg) {
    char operPl = *((char*) arg);
    int n1, n2, n3;
    sem_wait(&sem2); // Ожидание сигнала от потока 1
    if (operPl == '+') {
        s2 = n1 + n2 + n3;
    }
    sem_post(&sem3); // Отправка сигнала потоку 3
    pthread_exit(NULL);
}

// Поток 3
void* thread3(void* arg) {
    char operStep = *((char*) arg);
    int n1, n2, n3;
    sem_wait(&sem3); // Ожидание сигнала от потока 2
    if (operStep == '^') {
        s3 = pow(2, n1) + pow(2, n2) + pow(2, n3);
    }
    sem_post(&sem1); // Отправка сигнала главному потоку
    pthread_exit(NULL);
}

В этом коде переменные operYm, operPl, operStep, n1, n2, n3, s1, s2, s3 и result передаются в функции потоков через аргументы. Теперь они будут видны и доступны внутри функций потоков.