Функция ExtractShortPathName()
Функция конвертирует длинное имя файла в DOS-формат, так называемый, 8.3. Этот формат подразумевает, что имя файла или папки может быть длиной максимум 8 символов, а затем, после точки, может присутствовать расширение имени файла из 3-х символов. Если имя папки (файла) имеет больше символов, оно будет обрезано до 8 символов.
Если указанный файл или каталог не существует, то функция возвращает пустую строку. Параметр может представлять собой полное имя файла. Если указанный файл не существует, то функция возвращает пустую строку. Пример:
var
S: string;
begin
...
S:= ExtractShortPathName( 'C:\Program Files\Accessories\wordpad.exe');
//Результат: S= C:\PROGRA~1\ACCESS~1\WORDPAD.EXE
...
end;
Процедура ProcessPath()
Процедура анализирует полное имя файла и возвращает отдельно имя диска, каталог и имя файла. Если файл не существует, то возникает ошибка. Когда полное имя файла содержит больше одного каталога, также возникает ошибка.
var
Dir, S: string; //для имени папки и имени файла
Drive: Char; //для имени диска (буквы A-Z)
begin
...
ProcessPath('C:\DIR1\work.txt', Drive, Dir, S); // Drive= 'C'; Dir= '\DIR1'; S= 'work.txt'
...
end;
Функция ExtractFileDrive()
Функция возвращает имя диска, извлеченное из полного имени файла. Если указанное имя файла не содержит имя диска, то функция возвращает пустую строку. Для имени в UNC формате (сетевое имя) возвращается строка в формате '\\<имя сервера>\<имя ресурса>'.
var
S: string;
begin
...
S:= ExtractFileDrive( 'C:\DIR1\myfile.zzz'); //S= 'C:'
...
end;
Функция ExtractFileExt()
Функция возвращает расширение файла, имя которого указано в параметре. Результирующая строка включает в себя символ точки и символы расширения файла. Если указанное имя файла не имеет расширения, то функция возвращает пустую строку. Пример:
var
S1, S2 : string;
begin
...
S1:= ExtractFileExt( 'www.atrussk.ru/delphi/index.htm'); //S1='.htm'
S2:= ExtractFileExt( 'c:\dir1\myfile.txt'); //S2 ='.txt'
...
end;
Пишем программу
Чтобы усвоить, как работают эти функции, создадим новое приложение. Форму сразу переименуйте в fMain, а проект сохраните под названием fname в отдельной папке. На форму установите Edit, здесь будет отображаться полное имя файла. Сразу под ней установите Label, тут будет отображаться результат работы функций. Очистите текст и у Edit и у Label. Ниже бросьте на форму кнопку, и напишите на ней "Открыть файл". Рядом с ней бросьте OpenDialog, он нам понадобится для открытия нужного файла. Еще ниже сгруппируйте 6 кнопок, на которых напишите:
ExtractFileName
ExtractFilePath
ExtractShortPathName
ExtractFileDir
ExtractFileDrive
ExtractFileExt
Рис. 14.1. Внешний вид приложения
Создайте обработчик для кнопки "Открыть файл". Здесь мы напишем такой текст:
if OpenDialog1.Execute then begin
Edit1.Text := OpenDialog1.FileName; //записываем адрес и имя открытого файла
Label1.Caption := Edit1.Text; //копируем тоже самое в Label
end; //if
Далее поочередно пишем обработчики для оставшихся кнопок. Нажмите первую, и напишите:
Label1.Caption := ExtractFileName(Edit1.Text); //извлекаем имя файла
Для второй кнопки:
Label1.Caption := ExtractFilePath (Edit1.Text);
Остальные кнопки обрабатываются также – просто подставьте указанную на кнопке функцию, остальной код остается без изменений. Сохраните и скомпилируйте пример, посмотрите как он работает.
Лекция 15. Преобразования типов
В этой лекции вы познакомитесь с функциями преобразования одних типов данных в другие, научитесь создавать сложные выражения путем подстановки значений, познакомитесь с глобальной переменной DecimalSeparator и напишите приложение с серьезной защитой от некорректного ввода пользователем числа.
Преобразования типов
В любом языке программирования то и дело приходится преобразовывать один тип данных в другой. К примеру, нам требуется, чтобы пользователь ввел денежную сумму. Для этого нужно использовать вещественное число с учетом того, что могут быть копейки. Однако нет компонентов, которые позволят сразу ввести вещественное число, приходится пользоваться теми компонентами, которые позволяют ввести вещественное число в виде строки:
'123456,78'
Пользователь воспринимает это так, будто вводит сразу цифры, однако мы то знаем, что это строка только символов, изображающая число. И чтобы действительно превратить ее в число, приходится использовать преобразования типов. Некоторыми функциями, которые служат этим целям, мы уже пользовались, давайте упорядочим эти знания и изучим новые функции.
IntToStr()
Наиболее часто используемая функция. Как вы уже знаете, она принимает в качестве параметра целое число, и возвращает его в виде строки. Хотелось бы отметить еще одну особенность: эта функция предназначена для любого целого числа, не обязательноInteger. Если у вас есть переменная Byte, Word, Cardinal или Int64, все это переменные целого типа, и для любой из них годится функция IntToStr().
Примеры использования:
var
b : Byte;
w : Word;
i : Integer;
begin
b := 5;
w := 10;
i := 20;
Edit1.Text := IntToStr(b);
Edit2.Text := IntToStr(w);
ShowMessage(IntToStr(i));
end;
StrToInt()
Эта функция напротив, принимает в качестве параметра строку, изображающую целое число, и возвращает его в виде целого числа. Все, что было сказано о типах данных в функции IntToStr(), справедливо и для этой функции. Примеры использования:
var
b : Byte;
w : Word;
i : Integer;
begin
b := StrToInt(Edit1.Text); //внимание! Если пользователь введет число
//больше 255, произойдет ошибка!
w := StrToInt('50000');
i := StrToInt(Edit2.Text);
end;
Как видите, действия этих функций очень похожи, только в последнем случае приходится применять осторожность, чтобы не превысить диапазон возможных значений. Если вы заранее не знаете, какое число введет пользователь, лучше использовать Integer илиCardinal, если число без знака. Экономия памяти иной раз может вызвать серьезные ошибки в программе.
FloatToStr()
Эта функция принимает в качестве параметра вещественное число (то есть, число с запятой), и возвращает его в виде строки. Примеры применения почти аналогичны функции IntToStr(), однако есть одна особенность – если после запятой у Вас есть только нули, то функция вернет строку в виде целого числа:
s := FloatToStr(125,00); // результат: '125'
Эта функция также предназначена для всех типов вещественных чисел.
StrToFloat()
Эта функция принимает в качестве параметра строку в виде вещественного или целого числа, и возвращает это вещественное число. Пример:
f := StrToFloat('125'); //результат: 125,0
FormatFloat()
Эта функция по своему предназначению похожа на функцию FloatToStr(), однако она является гораздо более мощным инструментом. Эта функция не только возвращает вещественное число в качестве строки, но еще и позволяет задать желаемый формат этой строки. В прошлых примерах мы говорили, что функция FloatToStr() вместо строки '125,00' выведет '125'. А если нужно все-таки '125,00'? Такое сплошь и рядом встречается, особенно в финансовой документации. Для этих целей и создана функция FormatFloat.
Она имеет два параметра – строку формата и само число. Строка может содержать следующие форматы:
Таблица 15.1. Возможные форматы FormatFloat() | ||||
Строка, указываемая в формате | Примеры чисел | |||
-1234 | 0,5 | |||
-1234 | ||||
0.00 | 1234,00 | -1234,00 | 0,50 | 0,00 |
#.## | -1234 | 0,5 | ||
#,0.00 | 1 234,00 | -1 234,00 | 0,50 | 0,00 |
Есть и другие варианты форматов, например, для представления числа в экспонентной форме, но они, как правило, не используются.
Поясним строку форматов подробней.
В первом случае показаны варианты возвращаемых строк, если строка форматов вообще не указана.
"Решетка" (#) работает также, как "ноль", с той разницей, что если на этом месте не окажется цифры, то "решетка" ничего не выведет, а "ноль" подставит в это место ноль.
Знак запятая здесь указывают для удобного отображения разрядности числа. Например, миллион будет выглядеть как строка '1 000 000'. Заметим, что на само число этот формат не оказывает никакого влияния, он нужен только для того, чтобы выводить число в удобочитаемой форме в виде строки.
Примеры использования:
var
f : Real;
begin
f := 1234567,00;
ShowMessage(FormatFloat('0,000.00' ,f)); //результат: "1 234 567,00"
ShowMessage(FormatFloat(f)); //результат: "1234567"
end;
Другие преобразования
Иногда, чтобы преобразовать один тип данных в другой, достаточно указать этот тип:
var
p : PChar;
s : String;
begin
p := 'Строка';
s := String(p);
p := PChar(s);
В других случаях, схожие типы данных можно просто присваивать друг другу. Компилятор в этом случае сам произведет нужное преобразование. Например, целый тип данных можно присвоить вещественному числу, компилятор сам подставит ноль. А вот наоборот не получится, ведь вещественное число рассматривается, как два целых числа:
var
f : Real;
i : Integer;
begin
i := 12;
f := i; //Результат: 12,0
i := f; //Ошибка! Так нельзя
Подстановка значений
Очень часто в языках программирования для элегантности кода подставляют одно значение вместо другого. Сравните два примера:
var
s : String;
i : Integer;
begin
s := Edit1.Text;
i := StrToInt(s);
end;
Все, что мы сделали в данном примере, так это присвоили переменной i число из Edit1, которое хранилось там в виде строки. Но для этого нам пришлось вначале занести эту строку в строковую переменную s, и уже ее обрабатывать функцией StrToInt(). Такой пример вполне будет работать, однако он слишком громоздок. Гораздо элегантнее выглядит следующий код:
var
i : Integer;
begin
i := StrToInt(Edit1.Text);
end;
В результате получилось меньше переменных, меньше работы для процессора, меньше занимаемой памяти и короче код! А нередко употребляют гораздо более сложные выражения, например:
i := StrToInt(Memo1.Lines[5]) + StrToInt(Edit1.Text);
s := IntToStr(StrToInt(Memo1.Lines[5]) + StrToInt(Edit1.Text));
В первой строке в целую переменную i мы вывели сумму целых чисел, которые хранились в виде строки в Edit1 и в пятой строке Memo1.
Вторая строка сложнее. Здесь мы вначале перевели эти же числа в целые числа и суммировали их, затем вновь преобразовали в строку, чтобы записать сумму этих двух чисел в строковую переменную s. Поначалу вам такой код может показаться очень сложным, но попробуйте применять такой подход в своих программах, и вы быстро к нему привыкнете, и сами заметите, что такой код более компактен и элегантен. Возьмите вторую строку. Такой же результат можно было бы добиться упрощенными выражениями:
i := StrToInt(Memo1.Lines[5]);
k := StrToInt(Edit1.Text);
m := i + k;
s := IntToStr(m);
Все это будет работать, и на первый взгляд, кажется проще. Однако, четыре строки вместо одной! И четыре переменных вместо одной! Любой программист назовет такой код безобразным и дилетантским. Так что привыкайте к хорошему и компактному коду!