Предусмотреть следующие возможности корректировки по

ч. 1


Лабораторная работа №11

Задание:

Создать тип данных (в виде структуры на языке Си) в соответствии с условием задачи из списка ниже. Разработать программу, которая в интерактивном режиме выполняет команды пользователя: а) из текстового файла ввести все данные и создать двоичный файл; б) поиск в двоичном файле по условию задачи; в) коррекция данных в двоичном файле (не при вводе из текстового, а именно редактирование двоичного файла).

Предусмотреть следующие возможности корректировки по вариантам:
1. Вес и количество вещей не отрицательные и не более 50. При нулевом количестве вещей только нулевой вес.

2. Номер месяца 1-12, дней не более 28-31 в соответствии с месяцем.

3. Отметка о прохождении техосмотра включает и дату его прохождения. Техосмотр должен быть пройден не более чем год назад. Номер месяца 1-12, дней не более 28-31 в соответствии с месяцем.

4. Время отправления: минуты 0-59, часы 0-23.

5. Стаж 0-60 лет, и не больше возраста-15лет.
6. Возрастные границы: нижняя меньше верхней не менее чем на 2 года, не отрицательные и не более 150 лет.

7. Год издания не менее 1800, и не более нынешнего года.

8. Год издания не менее 1800, и не более нынешнего года. Запросов не отрицательное количество.

9. Номера телефонов только из цифр, и их не менее 6.

10. Проводимость только трех указанных видов, количество положительное.
11. В дате номер месяца 1-12, дней не более 28-31 в соответствии с месяцем, номер комнаты положительный.

12. Количество, имеющееся в наличии и заказанное, - положительные величины.

13. Номер месяца 1-12, дней не более 28-31 в соответствии с месяцем.

14. Номер заказа положительный, номер месяца 1-12, дней не более 28-31 в соответствии с месяцем.

15. Время поступления: часы 0-23, минуты и секунды 0-59.
16. Номер месяца 1-12, дней не более 28-31 в соответствии с месяцем. Номер квартиры положительное число.

17. Широта от -90 до 90, долгота от -180 до 180. Высота положительная.

18. Пол только мужской и женский, некорректный сделать мужским. Давление положительное.

19. Все дети не младше 5 лет и не старше 14 по году рождения, рост-вес положительные и не более 200.

20. Дом, квартира - положительные числа.
21. Часы работы: минуты 0-59, часы 6-21. Начало работы раньше завершения.

22. Начало работы раньше завершения. Часы работы: минуты 0-59, часы 0-23.

23. Размеры с 10 до 45, типов только три.

24. Возраст от 0 до 15, место не отрицательное.

25. Интервалы положительные и не более часа, среднее время не более двух часов.
26. В дате посещения номер месяца 1-12, дней не более 28-31 в соответствии с месяцем.

27. В дате рождения номер месяца 1-12, дней не более 28-31 в соответствии с месяцем. Отметки только двух видов: сделана по плану или не сделана.

28. Размеры с 20 по 60, рост 100-200.

29. Год окончания больше года поступления не менее чем на 4 года, но не больше нынешнего.

30. Год издания не раньше 1950 и не больше нынешнего.
Условия задачи:







Пример решения задачи.

Условие: Имеются сведения о студентах: фамилия, имя, отчество и оценки за три экзамена (физика, мат.анализ и программирование). Найти всех юношей по имени Иван, получивших по всем этим трём экзаменам пятёрки. Предусмотреть коррекцию: оценки лежат в диапазоне 2-5.


Далее приведен код на Delphi(две версии: для бестипового(двоичного) и типизированного файла) и Си (двоичный файл), поскольку на экзамене будет возможность выбора языка для решения подобной задачи.

Си (двоичный файл)

Аналог на Delphi (бестиповой файл)

#include

#include

#include

//------------------------------------------------------------

struct TStud {

struct {

char F[31], I[31], O[31];

} FIO;


int o1,o2,o3;

};

// ---------создание копии строки, но с символами



//---------------в верхнем регистре в Win1251

char *ANSIUpperCase(char *s, char *S){

S = strcpy(S, s);

char *ch=S;

while (*ch) {

if (*ch>='a' && *ch<='z' || *ch>='а' && *ch<='я') *ch= *ch-32;

if (*ch =='ё') *ch='Ё';

ch++;


}

return S;

}

//----------первая часть: создание двоичного из текстового



void CreateBinaryFile(int argc, char* argv[]){

if (argc<3) {

printf("Мало параметров\nPress any key");

getch();


return;

}
FILE *ft = fopen(argv[2], "rt");

if (ft==NULL) {

printf("Error: не удалось открыть файл с \

исходными данными %s\n", argv[2]);

printf("Press ENTER");

getch();

return;


}
FILE *fb = fopen(argv[1], "wb");

if (fb==NULL) {

printf("Error: не удалось создать \

двоичный файл %s\n", argv[1]);

printf("Press ENTER");

getch();


return;

}
TStud Stud; // либо struct TStud Stud;

int kol=0;

char s[3];

while (1){

fscanf(ft,"%30s", Stud.FIO.F);

if (strcmp(Stud.FIO.F,"**")==0) break;

//признак конца - фамилия **

fscanf(ft,"%30s", Stud.FIO.I);

fscanf(ft,"%30s", Stud.FIO.O);

fscanf(ft,"%s", s); Stud.o1=atoi(s);

fscanf(ft,"%s", s); Stud.o2=atoi(s);

fscanf(ft,"%s", s); Stud.o3=atoi(s);
fwrite(&Stud, sizeof(Stud), 1, fb);

kol++;


}
fclose(ft);

fclose(fb);


printf("Создан двоичный файл из %d записей \

по %d байт\n", kol, sizeof(TStud));

printf("Press any key to continue");

getch();

return;

}

//-------------- вторая часть: поиск в двоичном файле ----



void FindIVAN(int argc, char* argv[]){

if (argc<2) {

printf("Мало параметров\nPress any key");

getch();


return;

}

FILE *fb = fopen(argv[1], "rb");



if (fb==NULL) {

printf("Error: не удалось открыть двоичный \

файл %s\n", argv[1]);

printf("Press ENTER");

getch();

return;


}
TStud Stud;

char SUp[31];

int kol=0, nr=1;

while (nr){

nr=fread(&Stud, sizeof(Stud), 1, fb);

if (nr>0)

if (Stud.o1==5 && Stud.o2==5 && Stud.o3==5 &&

strcmp(ANSIUpperCase(Stud.FIO.I, SUp),"ИВАН")==0) {

printf("Найден %s %s %s\n", Stud.FIO.I, Stud.FIO.O, Stud.FIO.F);

kol++;


}

}

if (kol==0)



printf("Данные, соответствующие запросу,не найдены\n");

else


printf("Всего найдено: %d\n", kol);
fclose(fb);
printf("Press any key to continue");

getch();

return;

}

//-------третья часть: корректировка в двоичном файле ----



void CorrectFile(int argc, char* argv[]){

if (argc<2) {

printf("Мало параметров\nPress any key");

getch();


return;

}

FILE *fb = fopen(argv[1], "rb+");



if (fb==NULL) {

printf("Error: не удалось открыть двоичный файл %s\n", argv[1]);

printf("Press ENTER");

getch();


return;

}
TStud Stud;

int kol=0, nr=1, nw=1, flag;

nr=fread(&Stud, sizeof(Stud), 1, fb);

while (nr==1 && nw==1){

printf("Считана запись:\n");

printf("%25s%20s%25s%2d%2d%2d\n", Stud.FIO.F,

Stud.FIO.I, Stud.FIO.O, Stud.o1,Stud.o2,Stud.o3);


flag=0;

if (Stud.o1<2) {Stud.o1=2; flag=1;}

if (Stud.o2<2) {Stud.o2=2; flag=1;}

if (Stud.o3<2) {Stud.o3=2; flag=1;}


if (Stud.o1>5) {Stud.o1=5; flag=1;}

if (Stud.o2>5) {Stud.o2=5; flag=1;}

if (Stud.o3>5) {Stud.o3=5; flag=1;}
if (flag) {

kol++;


fseek(fb,-sizeof(Stud),SEEK_CUR);

nw=fwrite(&Stud, sizeof(Stud), 1, fb);

fseek(fb,0,SEEK_CUR);
printf("Сделана корректировка:\n");

printf("%25s%20s%25s%2d%2d%2d\n", Stud.FIO.F,

Stud.FIO.I,Stud.FIO.O,Stud.o1,Stud.o2, Stud.o3);

}

nr=fread(&Stud, sizeof(Stud), 1, fb);



}

if (kol==0)

printf("Ни одной корректировки\n");

else


printf("Всего корректировок: %d\n", kol);
fclose(fb);
printf("Press any key to continue");

getch();

return;

}

//------------------главная функция-----------------------



int main(int argc, char* argv[])

{

char ch;



SetConsoleOutputCP(1251);
do{
printf("\nN - создать новый тип.файл; F - сразу поиск;\

C - коррекция; E - конец.\nВаш выбор?");

ch=getchar(); fflush(stdin);

ch=toupper(ch);

switch (ch) {

//----------первая часть: создание двоичного из текстового

case 'N': CreateBinaryFile(argc, argv); break;

//-------------- вторая часть: поиск в двоичном файле ----

case 'F': FindIVAN(argc, argv); break;

//-------третья часть: корректировка в двоичном файле ----

case 'C': CorrectFile(argc, argv); break;

//-----------выход----------------------------------------

case 'E': return 0;

//--------------------------------------------------------

default:

printf("Нет такой команды\nPress any key");

getch();

}
} while (ch!='E');


return 0;

}

//-----------------------------------------------------------



program Project1;

{$APPTYPE CONSOLE}

uses

SysUtils, Windows;



//-----------------------------------------------------------

Type


TStud = record

FIO: record

F, I, O: string[30];

end;


o1,o2,o3: byte;

end;


//----------первая часть: создание двоичного из текстового

Procedure CreateBinaryFile();

var

Stud: TStud;



ft: TextFile;

fb: file; // бестиповой (двоичный) файл

kol,nw: integer;

begin


if ParamCount<2 then

begin


writeln('Мало параметров '#13#10'Press enter');

readln; exit

end;
AssignFile(ft, ParamStr(2));

{$I-} Reset(ft); {$I+}

if IOResult<>0 then

begin


writeln('Error: не удалось открыть файл ',

'с исходными данными ',ParamStr(2));

write('Press ENTER'); readln; exit

end;
AssignFile(fb, ParamStr(1));

{$I-} ReWrite(fb,sizeof(TStud));{$I+}

// или при открытии 1, а при вводе,выводе SizeOf

if IOResult<>0 then

begin


CloseFile(ft);

writeln('Error: не удалось создать двоичный ',

'файл ',ParamStr(1));

write('Press ENTER'); readln; exit

end;
kol:=0; nw:=1;

while not seekeof(ft) and (nw=1) do

begin

readln(ft, Stud.FIO.F);



readln(ft, Stud.FIO.I);

readln(ft, Stud.FIO.O);

readln(ft, Stud.o1,Stud.o2,Stud.o3);
BlockWrite(fb, Stud, 1, nw);

inc(kol)


end;

if nw<>1 then writeln('Error: Ошибка при записи');


CloseFile(ft);

CloseFile(fb);


writeln('Создан двоичный файл из ',kol,

' записей по ',sizeof(TStud),' байт');

write('Press ENTER'); readln;

end;


//-------------- вторая часть: поиск в двоичном файле ----

Procedure FindIVAN();

var

Stud: TStud;



fb: file;

kol, nr: integer;

begin

if ParamCount<1 then



begin

writeln('Мало параметров '#13#10'Press enter');

readln; exit

end;
AssignFile(fb, ParamStr(1));

{$I-} ReSet(fb, sizeof(TStud));{$I+}

// или здесь при открытии 1, а при вводе,выводе SizeOf

if IOResult<>0 then

begin


writeln('Error: не удалось открыть двоичный файл ', ParamStr(1));

write('Press ENTER'); readln; exit

end;
kol:=0; nr:=1;

while not eof(fb) and (nr=1) do

begin

BlockRead(fb, Stud, 1, nr);



if nr>0 then

if (Stud.o1=5) and (Stud.o2=5) and (Stud.o3=5) and

(ANSIUpperCase(Stud.FIO.I) = 'ИВАН') then

begin


writeln('Найден ', Stud.FIO.I,' ',Stud.FIO.O,' ', Stud.FIO.F);

inc(kol)


end;

end;


if nr<>1 then writeln('Error: ошибка при считывании');

if kol=0 then

writeln('Данные, соответствующие запросу, не найдены')

else


writeln('Всего найдено: ',kol);
CloseFile(fb);

write('Press ENTER'); readln;

end;

//-------третья часть: корректировка в двоичном файле ----



Procedure CorrectFile();

var


Stud: TStud; fb: file; flag: boolean;

kol, nr,nw,so: integer;

begin

if ParamCount<1 then



begin

writeln('Мало параметров '#13#10'Press enter');

readln; exit

end;
AssignFile(fb, ParamStr(1));

{$I-} ReSet(fb, 1);{$I+}

// или как выше здесь sizeof, а при чтении/записи 1

if IOResult<>0 then

begin


writeln('Error: не удалось открыть типизированный файл ', ParamStr(1));

write('Press ENTER'); readln; exit

end;
kol:=0; so:=sizeof(TStud); nr:=so; nw:=so;

while not eof(fb) and (nr=so) and (nw=so) do

begin

BlockRead(fb, Stud, so, nr);


writeln('Считана запись:');

writeln(Stud.FIO.F:25, Stud.FIO.I:20, Stud.FIO.O:25, Stud.o1:2,Stud.o2:2,Stud.o3:2);


flag:=false;

if (Stud.o1<2) then begin Stud.o1:=2; flag:=true end;

if (Stud.o2<2) then begin Stud.o2:=2; flag:=true end;

if (Stud.o3<2) then begin Stud.o3:=2; flag:=true end;


if (Stud.o1>5) then begin Stud.o1:=5; flag:=true end;

if (Stud.o2>5) then begin Stud.o2:=5; flag:=true end;

if (Stud.o3>5) then begin Stud.o3:=5; flag:=true end;
if flag then

begin


inc(kol);

seek(fb, FilePos(fb)-so);

BlockWrite(fb, Stud, nr, nw);
writeln('Сделана корректировка:');

writeln(Stud.FIO.F:25, Stud.FIO.I:20, Stud.FIO.O:25, Stud.o1:2,Stud.o2:2,Stud.o3:2);

end;

end;


if nw<>so then writeln('Error: ошибка при чтении ',

' или записи');


if kol=0 then

writeln('Ни одной корректировки')

else

writeln('Всего корректировок: ',kol);


CloseFile(fb);

write('Press ENTER'); readln;

end;

//--------------------главная программа--------------------



var

ch: char;

begin

SetConsoleOutputCP(1251);



repeat
write('N - создать новый тип.файл; F - сразу поиск;',

' C - коррекция; E - конец.',

#13#10'Ваш выбор?');

readln(ch);

ch:= UpCase(ch);

case ch of

//----------первая часть: создание двоичного из текстового

'N': CreateBinaryFile;

//----------вторая часть: поиск в двоичном файле ---------

'F': FindIVAN;

//----------третья часть: корректировка в двоичном файле -

'C': CorrectFile;

//-----------выход----------------------------------------

'E': exit;

//--------------------------------------------------------

else


begin

writeln('Нет такой команды');

write('Press ENTER'); readln;

end;


end;
until ch='E';

end.

Со следующей страницы код на Delphi с типизированным файлом:


Аналог на Delphi с типизированным файлом

program Project1;
{$APPTYPE CONSOLE}
uses

SysUtils, Windows;

//--------------------------------------------------------------

Type


TStud = record

FIO: record

F, I, O: string[30];

end;


o1,o2,o3: byte;

end;


//----------первая часть: создание типизированного из текстового

Procedure CreateTypedFile();

var

Stud: TStud;



ft: TextFile;

fb: file of TStud; // типизированный файл – файл записей

kol: integer;

begin


if ParamCount<2 then

begin


writeln('Мало параметров '#13#10'Press enter');

readln; exit

end;
AssignFile(ft, ParamStr(2));

{$I-} Reset(ft); {$I+}

if IOResult<>0 then

begin


writeln('Error: не удалось открыть файл с исходными данными ',ParamStr(2));

write('Press ENTER'); readln; exit

end;
AssignFile(fb, ParamStr(1));

{$I-} ReWrite(fb);{$I+}

if IOResult<>0 then

begin


CloseFile(ft);

writeln('Error: не удалось создать типизированный файл ',ParamStr(1));

write('Press ENTER'); readln; exit

end;
kol:=0;

while not seekeof(ft) do

begin


readln(ft, Stud.FIO.F);

readln(ft, Stud.FIO.I);

readln(ft, Stud.FIO.O);

readln(ft, Stud.o1,Stud.o2,Stud.o3);


write(fb, Stud);

inc(kol)


end;
CloseFile(ft);

CloseFile(fb);


writeln('Создан типизированный файл из ',kol,' записей');

write('Press ENTER');

readln;

end;


//--------------------------------------------------------------

//-------------- вторая часть: поиск в типизированном файле ----

Procedure FindIVAN();

var


Stud: TStud;

fb: file of TStud;

kol: integer;

begin


if ParamCount<1 then

begin


writeln('Мало параметров '#13#10'Press enter');

readln; exit

end;
AssignFile(fb, ParamStr(1));

{$I-} ReSet(fb);{$I+}

if IOResult<>0 then

begin


writeln('Error: не удалось открыть типизированный файл ',ParamStr(1));

write('Press ENTER'); readln; exit

end;

kol:=0;


while not eof(fb) do

begin


read(fb, Stud);
if (Stud.o1=5) and (Stud.o2=5) and (Stud.o3=5) and

(ANSIUpperCase(Stud.FIO.I) = 'ИВАН') then

begin

writeln('Найден ', Stud.FIO.I,' ',Stud.FIO.O,' ',Stud.FIO.F);



inc(kol)

end;


end;
if kol=0 then

writeln('Данные, соответсвующие запросу, не найдены')

else

writeln('Всего найдено: ',kol);


CloseFile(fb);
write('Press ENTER'); readln;

end;


//--------------------------------------------------------------

//-------третья часть: корректировка в типизированном файле ----

Procedure CorrectFile();

var


Stud: TStud;

fb: file of TStud;

kol: integer;

flag: boolean;

begin

AssignFile(fb, ParamStr(1));



{$I-} ReSet(fb);{$I+}

if IOResult<>0 then

begin

writeln('Error: не удалось открыть типизированный файл ',ParamStr(1));



write('Press ENTER'); readln;

exit


end;
kol:=0;

while not eof(fb) do

begin

read(fb, Stud);


writeln('Считана запись:');

writeln(Stud.FIO.F:25, Stud.FIO.I:20, Stud.FIO.O:25,

Stud.o1:2,Stud.o2:2,Stud.o3:2);
flag:=false;

if (Stud.o1<2) then begin Stud.o1:=2; flag:=true end;

if (Stud.o2<2) then begin Stud.o2:=2; flag:=true end;

if (Stud.o3<2) then begin Stud.o3:=2; flag:=true end;


if (Stud.o1>5) then begin Stud.o1:=5; flag:=true end;

if (Stud.o2>5) then begin Stud.o2:=5; flag:=true end;

if (Stud.o3>5) then begin Stud.o3:=5; flag:=true end;
if flag then

begin


inc(kol);

seek(fb, FilePos(fb)-1);

write(fb, Stud);
writeln('Сделана корректировка:');

writeln(Stud.FIO.F:25, Stud.FIO.I:20, Stud.FIO.O:25,

Stud.o1:2,Stud.o2:2,Stud.o3:2);

end;


end;
if kol=0 then

writeln('Ни одной корректировки')

else

writeln('Всего корректировок: ',kol);


CloseFile(fb);

write('Press ENTER'); readln;

end;

//--------------------главная программа-------------------------



var

ch: char;

begin

SetConsoleOutputCP(1251);



repeat
write('N - создать новый тип.файл; F - сразу поиск; C - коррекция; E - конец.',

#13#10'Ваш выбор?');

readln(ch);

ch:= UpCase(ch);

case ch of

//--------------------------------------------------------------

//----------первая часть: создание типизированного из текстового

'N': CreateTypedFile;

//----------вторая часть: поиск в типизированном файле ---------

'F': FindIVAN;

//----------третья часть: корректировка в типизированном файле -

'C': CorrectFile;

//-----------выход----------------------------------------------

'E': exit;

//--------------------------------------------------------------

else


begin

writeln('Нет такой команды');

write('Press ENTER'); readln;

end;


end;
until ch='E';

end.

ч. 1