/********************* Файл LAB3.C ****************************/
/* Для сокращения записи типа структуры введем следующую константу */
#define emlp struct _emlp
#define _CRT_SECURE_NO_WARNINGS
/* Функция печати списка */
int f_print();
/* Функция ввода списка */
int f_input();
/* Добавление элемента в список */
int f_add();
/* Уничтожение элемента списка */
int f_delete();
/* Изменение значения полей элемента списка */
int f_change();
/* Функция сортировки списка */
int f_sort();
/* Функция сохранения списка на диске */
int f_save();
/* Перезапись списка из файла в динамическую память */
int f_restore();
#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#include <locale.h>
/* Описание структуры */
emlp{
char name[25]; /* Ф.И.О. */
int grade; /* Должность */
int hight; /* Звание */
emlp *next; /* Указатель на следующий элемент */
};
emlp *emlph = NULL; /* Начало списка */
char fname[] = "D_STRUCT.DA1"; /* Файл для хранения списка */
int main() {
char eoj; /* Флаг окончания работы */
int i; /* Вспомогательная переменная */
/* Структура меню */
struct {
int op; /* Номер операции */
int(*opf)(); /* Функция обработки */
} m[9] = {
{ '1', f_print }, { '2', f_input }, { '3', f_add },
{ '4', f_delete }, { '5', f_change }, { '6', f_sort },
{ '7', f_save }, { '8', f_restore }, { '0', }
};
int opcode; /* Код операции */
for (;;) { /* Пока не конец работы */
/* Очистка экрана */
printf("1. Print\n"); /* Вывод пунктов меню на экран */
printf("2. Input\n");
printf("3. Add\n");
printf("4. Delete\n");
printf("5. Change\n");
printf("6. Sort\n");
printf("7. Save\n");
printf("8. Restore\n");
printf("0. Quit\n");
printf("Enter operation code > "); /* Запрос на ввод номера
пункта для выполнения */
opcode = getchar(); /* Ввод номера пункта */
putchar('\n');
if (opcode == '0') { /* выход из программы,
если выбран QUIT */
printf("Press any key...");
getchar();
exit(0);
}
for (i = 0; i < 10; i++){ /* Запуск соответствующей функции
обработки */
if (opcode == m[i].op) {
if (m[i].opf() == 1) exit(0);
break;
}
}
}
}
/****************************************************************/
/**************** Функция вывода списка на экран ****************/
/****************************************************************/
int f_print() {
emlp *a; /* Указатель на структуру */
int i, j;
/* Если списка нет в памяти,то вывод соотвтствуюшего
сообщения */
/* Иначе - вывод всего списка на экран */
if (emlph == NULL) printf("List empty\n");
else {
for (a = emlph, i = 1, j = 1; a != NULL; a = a->next, j++, i++) {
printf("#%-2d %-10s %-4d %-4d\n",
i, a->name, a->grade, a->hight);
if (j == 20){
printf("Press any key for continue...\n");
getchar();
j = 1;
}
}
printf("======= end of list ========\n");
}
return 0;
}
/****************************************************************/
/*********** Функция ввода элементов списка **********************/
/****************************************************************/
int f_input() {
int cc;
printf("Enter name=* for end of stream\n");
/* Конец ввода - при вводе '*' вместо имени */
while (!(cc = f_add())); /* Вызов функции добавления */
return cc;
}
/****************************************************************/
/************* Добавление элемента в список *********************/
/****************************************************************/
int f_add() {
emlp *a, *b;
char ss[40];
int i = 1;
/* Если список существует,осуществляем вставку элемента */
if (emlph != NULL)
for (i++, a = emlph; a->next != NULL; a = a->next, i++);
/* Приглашение к вводу */
printf("Line #%d. Enter: name grade hight >", i);
scanf("%s", ss);
if (ss[0] == '*') return 2;
/* Выделение памяти под новый элемент */
b = (emlp *)malloc(sizeof(emlp));
strcpy(b -> name, ss);
scanf("%d %d", &(b->grade), &(b->hight));
b->next = NULL;
/* Элемент вставляется после головы списка или в начало,
если список пустой */
if (emlph == NULL) emlph = b;
else a->next = b;
return 0;
}
/*****************************************************************/
/************ Функция сохранения списка на диске *****************/
/*****************************************************************/
int f_save() {
FILE *dat;
emlp *a;
dat = fopen(fname, "w"); /* Открытие файла на запись */
/* Запись в файл осуществляется полями */
for (a = emlph; a != NULL; a = a->next)
fprintf(dat, "%s %d %d\n", a->name, a->grade, a->hight);
/* В конце файла - спецкод '***' */
fprintf(dat, "***\n");
fclose(dat); /* Закрытие файла */
return 0;
}
/****************************************************************/
/****** Перезапись списка из файла в динамическую память ********/
/****************************************************************/
int f_restore() {
FILE *dat;
char ss[40];
emlp *a, *b;
/* Открытие файла для чтения,если файл не найден-вывод
соответствующего сообщения */
if ((dat = fopen(fname, "r")) == NULL) {
printf("File not found : %s\n", fname);
return 1;
}
else {
emlph = NULL;
do {
/* Чтение из файла по полям пока не дошли до
спецкода '* '*/
fscanf(dat, "%s", ss);
if (ss[0] != '*') {
/* Выделение памяти под новый элемент */
b = (emlp *)malloc(sizeof(emlp));
if (emlph == NULL) emlph = b;
else a->next = b;
strcpy(b->name, ss);
fscanf(dat, "%d %d\n", &(b->grade), &(b->hight));
b->next = NULL;
a = b;
}
} while (ss[0] != '*');
fclose(dat); /* Закрытие файла */
}
return 0;
}
/*****************************************************************/
/*************** Функция сортировки списка ***********************/
/*****************************************************************/
int f_sort() {
int n;
emlp *a, *b, *c;
/* Если список пустой или в нем один элемент,
то выход из функции */
c = malloc(sizeof(emlp));
if ((emlph == NULL) || (emlph->next == NULL)) return 0;
/* Сортировка списка методом "пузырька" */
for (n = 1; n;) {
n = 0;
for (a = emlph, b = emlph->next; b != NULL;)
if (strcmp(a->name, b->name)>0) {
a->next = b->next; b->next = a;
if (a == emlph) emlph = b;
else c->next = b;
c = b; b = a->next;
n = 1;
}
else {
c = a; a = b; b = b->next;
}
}
return 0;
}
/*****************************************************************/
/************ Ввод номера элемента *******************************/
/*****************************************************************/
int get_ln() {
int ln;
printf("Enter line number >");
do {
/* Ввод номера элемента и проверка его(если он меньше единицы-
выдается сообщение об ошибке */
scanf("%d", &ln);
if (ln<1) {
printf("Illegial line number. Try again >");
ln = 0;
}
} while (!ln);
return ln;
}
/*****************************************************************/
/************* Уничтожение элемента списка ***********************/
/*****************************************************************/
int f_delete() {
int ln;
emlp *a, *b;
/* Если списка нет в памяти,то вывод соотвтствуюшего
сообщения */
if (emlph == NULL) printf("List empty\n");
/* Иначе-ввод номера элемента с помощью функции GET_LN */
else {
ln = get_ln() - 1;
if (!ln) {
/* Если номер корректен - переприсваивание указателей
и освобождение памяти */
a = emlph; emlph = a->next; free(a);
}
else {
/* Иначе- ??????? */
for (ln--, a = emlph; ln && (a != NULL); a = a->next, ln--);
if (a != NULL)
if ((b = a->next) != NULL) {
a->next = b->next; free(b);
}
}
}
return 0;
}
/*****************************************************************/
/********** Изменение значения полей элемента списка *************/
/*****************************************************************/
int f_change() {
char ss[40];
int ln;
emlp *a;
ln = get_ln() - 1; /* Ввод номера элемента */
for (a = emlph; ln && a != NULL; ln--, a = a->next);
if (ln) return 0;
/* Вывод старых и ввод новых значений */
/* Запись новых значений в список */
printf("Old name = %s New name >", a->name);
gets(ss);
if (*ss) strcpy(a->name, ss);
printf("Old grade = %d New grade >", a->grade);
gets(ss);
if (*ss) sscanf(ss, "%d", &(a->grade));
printf("Old hight = %d New hight >", a->hight);
gets(ss);
if (*ss) sscanf(ss, "%d", &(a->hight));
return 0;
}
main.c:131:3: warning: implicitly declaring library function 'strcpy'
with type 'char *(char *, const char *)'
[-Wimplicit-function-declaration]
strcpy(b -> name, ss);
^
main.c:131:3: note: include the header <string.h> or explicitly provide a
declaration for 'strcpy'
main.c:203:8: warning: implicitly declaring library function 'strcmp'
with type 'int (const char *, const char *)'
[-Wimplicit-function-declaration]
if (strcmp(a->name, b->name)>0) {
^
main.c:203:8: note: include the header <string.h> or explicitly provide a
declaration for 'strcmp'
main.c:275:3: warning: implicit declaration of function 'gets' is invalid
in C99 [-Wimplicit-function-declaration]
gets(ss);