Опубликован: 07.04.2008 | Уровень: специалист | Доступ: платный
Лекция 21:

Записи

< Лекция 20 || Лекция 21 || Лекция 22 >
Аннотация: В этой лекции вы познакомитесь с записями. Записи – очень удобный тип, важность которого трудно переоценить. Вы создадите свой тип записи, глобальную переменную этого типа и даже типизированный файл, в который будете сохранять эту запись, и считывать ее.

Записи

Запись – это структура данных, состоящая из полей различного типа. Можно сказать, что запись – это мини-объект, который имеет свойства, но не имеет методов и событий. Для чего нужны записи? Да много для чего. Их можно использовать для сохранения настроек программы вместо ini-файлов, из записей можно сделать небольшую базу данных на пользователей программы, и так далее. Использование записей ограничено только воображением программиста.

Записи объявляются в разделе type перед разделом var, и могут быть как локальными для процедур и функций, так и глобальными. Разумеется, если вы используете записи для сохранения параметров программы, желательно их делать глобальными. В языке C / C++ такой тип называется структурой, а в Delphi – записью. Синтаксис объявления записи следующий:

type
<имя_записи> = record
   ...; //описание полей
end;  //record

Однако мало описать такую запись, потом нужно еще объявить переменную типа этой записи:

var
   myPerem : имя_записи;

В дальнейшем можно обращаться к отдельным полям записи, указывая эту переменную:

myPerem.имя_поля

Давайте посмотрим, как можно сохранить в записи размеры и положение формы. Создайте новый проект. Перед разделом глобального блока var создайте раздел type. Неважно, что выше уже есть такой раздел, мы можем создать еще один, главное, чтобы он был перед var.

type
  myForm = record
    Left : Integer;
    Top : Integer;
    Width : Integer;
    Height : Integer;
  end; // record

Теперь у нас есть описанная запись myForm, в которой имеется 4 поля: Left, Top, Width и Height. Как вы уже догадались, в эти поля мы будем записывать положение и размеры формы.

Теперь внимание! Запись – это фактически новый тип данных! Мы можем объявить сколько угодно переменных типа myForm, а также использовать типизированный файл, присвоив ему тип myForm. Посмотрите на следующие примеры:

var
    perem : myForm;  //переменная нашего типа
    ar : array [0..10] of myForm;  //массив
    f : File of myForm;  //типизированный файл

Вернемся к нашему проекту. Ниже записи имеется глобальный раздел var, где описана переменная Form1. Ниже нее добавим еще одну переменную:

myF : myForm;

Теперь мы можем при разрушении формы создать двоичный файл, в котором будут сохраняться положение и размер формы. Создайте обработчик событий onDestroy для формы, и в нем напишите следующий код:

var
  f : File of myForm;  //типизированный файл
begin
  //сохраняем данные в запись:
  myF.Left := Form1.Left;
  myF.Top := Form1.Top;
  myF.Width := Form1.Width;
  myF.Height := Form1.Height;

  //создаем или перезаписываем файл:
try
  AssignFile(f, 'my.dat');
  Rewrite(f);
  Write(f, myF);
finally
  CloseFile(f);
end; // try

Обратите внимание, что мы не делаем проверку на существование файла, поскольку если файла нет, он будет создан, а если есть – перезаписан. Кроме того, в качестве имени мы используем строку 'my.dat'. Файл с таким именем будет создан в текущей папке. Поскольку наша программа не меняет папок, то текущей будет являться та, в которой находится программа. Сохраните проект, скомпилируйте, посмотрите, как работает программа. Закройте ее и файловым менеджером перейдите в папку с проектом. Посмотрите, появился ли файл my.dat, попробуйте его прочитать.

Как видите, данные в файле хранятся в двоичном виде, что-либо прочитать там довольно сложно. Иногда удобней пользоваться таким способом, потому что всегда может найтись пользователь, который попытается играть с настройками в текстовых файлах. Ini – файлы имеют текстовый тип, и пользователь будет иметь возможность изменять там настройки вручную. Неважно, если мы сохраняем только размеры и положение формы, но мы можем сохранять и другие, более серьезные параметры! Однако пароли напрямую сохранять не получится – текст все же будет виден.

Насчет текста... Тип string имеет динамический характер. Другими словами, размер переменной такого типа может изменяться в процессе работы программы. Тип динамического характера (строка String или динамический массив) можно указать в записи, однако его нельзя использовать в типизированном файле, так как размер поля должен быть заранее известен.

Перейдем в раздел, где мы описывали наш тип данных. После описания поля Height опишем еще одно поле:

Caption : String[50]; //размер строки задан жестко, его можно использовать в файле

Теперь перейдем в обработку события onDestroy, и добавим строку:

myF.Caption := Form1.Caption;

в разделе сохранения данных в запись. Еще раз сохраните, откомпилируйте и запустите программу. Закройте ее и посмотрите на файл my.dat. Как видите, надпись в заголовке формы появляется в файле без изменений, так что любые ваши пароли все-таки можно будет прочитать. Измените заголовок формы, снова скомпилируйте проект и посмотрите в файл – строка по-прежнему читается.

Теперь нам нужно при открытии формы применить все эти настройки. Если вы помните пример с ini – файлом, настройки мы применяли в событии формы onCreate, также поступим и здесь. Создайте это событие для формы. Здесь нам придется проверять наличие файла – ведь если программа запускалась у клиента впервые, то файла там еще не было, он будет создан при закрытии программы. Поэтому будем применять настройки в том случае, если файл существует.

var
  f : File of myForm;
begin
  //если файла нет - выходим:
  if not FileExists('my.dat') then Exit;
 
 //открываем файл и считываем настройки в запись:
try
  AssignFile(f, 'my.dat');
  Reset(f);
  Read(f, myF); //считываем запись в нашу глобальную переменную
finally
  CloseFile(f);
end; //try

  //применяем полученные настройки:
  Form1.Left := myF.Left;
  Form1.Top := myF.Top;
  Form1.Height := myF.Height;
  Form1.Width := myF.Width;
  Form1.Caption := myF.Caption;
end;

Конечно, в типизированный файл можно сохранять более одной записи, однако такой прием мы изучим после того, как познакомимся с динамическими массивами.

Такой способ сохранения параметров кажется менее удобным, чем ini-файлы, однако компенсируется тем, что здесь можно сохранять данные любого типа – строки и даты, целые и вещественные числа, логические данные и даже массивы.

Самостоятельно измените программу. Добавьте на форму один CheckBox, состояние которого (включен или нет) будем сохранять в файл. Добавьте в запись еще одно поле логического типа, и в зависимости от того, установлена ли галочка в CheckBox, записывайте в него либо True, либо False.

< Лекция 20 || Лекция 21 || Лекция 22 >
Виктор Пелих
Виктор Пелих

Здравствуйте.
Прохожу курс "Введение в программирование на Delphi"
Добрался до Лекции 29: Введение в базы данных.

Установлена RAD Studio 11.3, у которой отсутствует вкладка BDE и, соответственно, компонент Table,  который обеспечивает доступ к таблице средствами механизма BDE.
Поиск в интернете подсказал 
BDE Installer for RAD Studio, Delphi, C++Builder 10.3 Rio
Подскажите, имеется ли ещё возможность использовать механизм BDE в Delphi11 и если такая возможность есть, как подключить BDE к Delphi11?
С уважением...

 

Федор Антонов
Федор Антонов

Здравствуйте!

Записался на ваш курс, но не понимаю как произвести оплату.

Надо ли писать заявление и, если да, то куда отправлять?

как я получу диплом о профессиональной переподготовке?

Надежда Таргын
Надежда Таргын
Россия, Кызыл
Оксана Прохорова
Оксана Прохорова
Россия, Уфа, УГАТУ, 1995