usaa24/cv7/program.c

132 lines
5.5 KiB
C
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define SIZE 256
// Структура для вузла дерева
struct tree {
char value[SIZE]; // Текст питання або твердження
struct tree *left; // Лівий підвузол
struct tree *right; // Правий підвузол
int id; // Ідентифікатор вузла
};
// Функція для знищення дерева та звільнення пам'яті
void destroy_tree(struct tree *tree) {
if (tree == NULL) return; // Якщо вузол порожній, нічого не робимо
destroy_tree(tree->left); // Рекурсивно знищуємо лівий підвузол
destroy_tree(tree->right); // Рекурсивно знищуємо правий підвузол
free(tree); // Звільняємо пам'ять, виділену для поточного вузла
}
// Функція для підрахунку кількості листових елементів (відповідей) в дереві
int count_items(struct tree *tree) {
if (tree == NULL) return 0; // Якщо вузол порожній, повертаємо 0
if (tree->left == NULL && tree->right == NULL) return 1; // Якщо вузол є листом (не має підвузлів), то це відповідь
return count_items(tree->left) + count_items(tree->right); // Рекурсивно підраховуємо кількість листових елементів
}
// Основна функція для запуску системи рішень
void run_system(struct tree *node) {
if (node == NULL) return; // Якщо вузол порожній, припиняємо виконання
int empty_lines = 0; // Лічильник порожніх рядків
int first_prompt = 1; // Флаг для виведення першого підказки
// Основний цикл, який буде працювати, поки є вузли в дереві
while (node != NULL) {
// Якщо вузол є листом (в кінці дерева)
if (node->left == NULL && node->right == NULL) {
printf("%s", node->value); // Виводимо відповідь
printf("Koniec\n"); // Завершуємо програму
return;
}
// Перший запит до користувача, вибір між двома варіантами
if (first_prompt) {
printf("Odpovedajte 'a' pre prvu moznost alebo 'n' pre druhu moznost.\n");
first_prompt = 0; // Встановлюємо флаг, щоб підказка виводилась тільки один раз
}
printf("%s", node->value); // Виводимо питання
char answer;
int result = scanf(" %c", &answer); // Читаємо відповідь користувача
// Перевірка на кінець вводу або два порожні рядки поспіль
if (result == EOF || (answer == '\n' && ++empty_lines >= 2)) {
printf("Koniec vstupu\n");
return; // Завершуємо виконання програми
}
// Обробка відповіді користувача
if (answer == 'a') {
empty_lines = 0; // Скидаємо лічильник порожніх рядків
node = node->left; // Переходимо до лівого підвузла
} else if (answer == 'n') {
empty_lines = 0; // Скидаємо лічильник порожніх рядків
node = node->right; // Переходимо до правого підвузла
} else {
printf("Nerozumiem\n"); // Якщо відповідь неправильна
return; // Завершуємо програму
}
}
}
// Функція для читання дерева з вводу
struct tree* read_tree() {
char buffer[SIZE];
memset(buffer, 0, SIZE);
// Read a line from stdin
char* r = fgets(buffer, SIZE, stdin);
if (r == NULL) {
// fprintf(stderr, "Chybna databaza\n");
exit(1); // Exit the program if reading fails
}
// Allocate memory for a new tree node
struct tree* node = calloc(1, sizeof(struct tree));
if (!node) {
printf("Memory allocation failed!\n");
exit(1);
}
// Copy the input line into the node's value
memcpy(node->value, buffer, SIZE);
// If the line is a leaf node (starts with '*'), no further questions are needed
if (buffer[0] == '*') {
return node; // Leaf node, no need to read further
}
// If not a leaf, recursively read the left and right child nodes
node->left = read_tree(); // Left child (yes answer)
node->right = read_tree(); // Right child (no answer)
return node;
}
int main() {
int counter = 0;
struct tree *root = read_tree(&counter); // Try reading the tree
printf("Expert z bufetu to vie.\n");
// Check if the tree was read successfully
if (root == NULL) {
printf("Chybna databaza\n");
return 0; // Exit if the tree couldn't be read
}
// If the tree was successfully read, count the number of items
int items_count = count_items(root);
printf("Pozna %d druhov ovocia a zeleniny.\n", items_count);
run_system(root); // Run the decision-making system
destroy_tree(root); // Free the allocated memory for the tree
return 0;
}