Иллюстрированный самоучитель по Delphi 6
7.1.2. Вещественные
типы
В отличие от порядковых типов, значения
которых всегда сопоставляются с рядом целых чисел и, следовательно, представляются
в ПК абсолютно точно, значения вещественных типов определяют произвольное число
лишь с некоторой конечной точностью, зависящей от внутреннего формата вещественного
числа.
Таблица 7.4. Вещественные
типы
Длина, байт
|
Название
|
Количество значащих цифр
|
Диапазон значений
|
8
4
8
10
8
8
|
Real
Single
Double
Extended
Comp
Currency
|
15…16
7…8
15…16
19…20
19…20
19…20
|
5.0*10e-324…1.7*10e308
1.5*10e-45…3.4*10e38
5.0*10e324…1.7*10e308
3.4*10-4951…1.1*10e4932
-2e63…+2e63-1
+/-922 337 203 685477,5807
|
Примечание
В предыдущих версиях Delphi 1...3
тип Real занимал 6 байт и имел диапазон значений от2, 9*10
-39
до
1,7*10
38
. В версиях 4 и 5 этот тип эквивалентен типу Double. Если
требуется (в целях совместимости) использовать 6-байтньш Real, нужно указать
директиву компилятора {SREALCOMPATIBILITY ON}.
Как видно из табл. 7.4, вещественное
число в Object Pascal занимает от 4 до 10 смежных байт и имеет следующую структуру
в памяти ПК:
Здесь s - знаковый разряд числа;
е - экспоненциальная часть; содержит двоичный порядок; m - мантисса числа.
Мантисса m имеет длину от 23 (для
single) до 63 (для Extended) двоичных разрядов, что и обеспечивает точность
7...8 для single и 19...20 для Extended десятичных цифр. Десятичная точка (запятая)
подразумевается перед левым (старшим) разрядом мантиссы, но при действиях с
числом ее положение сдвигается влево или вправо в соответствии с двоичным порядком
числа, хранящимся в экспоненциальной части, поэтому действия над вещественными
числами называют арифметикой с плавающей точкой (запятой).
Отметим, что арифметический сопроцессор
всегда обрабатывает числа в формате Extended, а три других вещественных типа
в этом случае получаются простым усечением результатов до нужных размеров и
применяются в основном для экономии памяти.
Например, если “машинное эпсилон”
(см. пример п. 5.4.3) вычисляется с помощью такой программы:
type
RealType = Real;
var
Epsilon : RealType;
begin
Epsilon := 1;
while
l+Eps4.1on/2
> 1 do
Epsilon := Epsilon/2;
IbOutput.Caption := FloatToStr(Epsilon)
end;
то независимо от объявления типа
RealType (он может быть single, Real, Double или Extended) на печать будет выдан
результат
1.08420217248550Е-0019
что соответствует типу Extended.
Происходит это по той причине, что все операнды вещественного выражения 1+Epsilon/2
в операторе while перед вычислением автоматически преобразуются к типу Extended.
Чтобы получить правильный результат, программу необходимо изменить следующим
образом:
type
RealType = Real;
var
Epsilon, Epsl : RealType;
begin
Epsilon := 1;
repeat
Epsilon := Epsilon/2;
Epsl := 1 + Epsilon
until
Epsl = 1;
IbOutput.Caption := FloatToStr(2*Epsilon)
end.
Особое положение в Object Pascal
занимают типы comp и Currency, которые трактуются как вещественные числа с дробными
частями фиксированной длины: в comp дробная часть имеет длину 0 разрядов, т.
е. просто отсутствует, в currency длина дробной части -4 десятичных разряда.
Фактически оба типа определяют большое целое число со знаком, сохраняющее 19...20
значащих десятичных цифр (во внутреннем представлении они занимают 8
смежных байт). В то же время в выражениях
comp и currency полностью совместимы с любыми другими вещественными типами:
над ними определены все вещественные операции, они могут использоваться как
аргументы математических функций и т. д. Наиболее подходящей областью применения
этих типов являются бухгалтерские расчеты.
Для работы с вещественными данными
могут использоваться встроенные математические функции, представленные в табл.
7.5. В этой таблице Real означает любой вещественный тип, integer - любой целый
тип.
Таблица 7.5. Стандартные
математические функции Object Pascal
Обращение
|
Тип параметра
|
Тип результата
|
Примечание
|
abs (x)
|
Real, Integer
|
Тип аргумента Real
|
Модуль аргумента
|
Pi
|
-
|
<<
|
П =3.141592653...
|
ArcTan(x)
|
|
|
Арктангенс (значение в радианах)
|
cos (x)
|
To же <<
|
To же <<
|
Косинус, угол в радианах
|
exp(x)
|
<<
|
<<
|
Экспонента
|
frac(x)
|
<<
|
<<
|
Дробная часть числа
|
int(x)
|
<<
|
<<
|
Целая часть числа
|
ln(x)
|
<<
|
<<
|
Логарифм натуральный
|
Random
|
-
|
<<
|
Псевдослучайное число, равномерно
распределенное в диапазоне 0...[1]
|
Random.fx)
|
Integer
|
Integer
|
Псевдослучайное целое число,
равномерно распределенное в диапазоне 0...(х-1)
|
Randomize
|
-
|
-
|
Инициация генератора псевдослучайных
чисел
|
sin (x)
|
Real
|
Real
|
Синус, угол в радианах
|
sqr(x)
|
To же
|
To же
|
Квадрат аргумента
|
sqrt(x)
|
<<
|
<<
|
Корень квадратный
|
Примечание
На заметку Генератор псевдо случайных
чисел представляет собой функцию которая берет некоторое целое число, называемое
базовым, изменяет, его разряды По определенному алгоритму и выдает новое число
результат. Одновременно с этим новое число становится базовым.прД следующем
обращении к функций; и т. д. (Так как алгоритм процедуры не меняется: в ходе
ее работы, числа называются псевдослучайна ми.) В системном модуле System,
который автоматически доступен любой программе, базовое число хранится в переменной
с именеД RandSeek и всегда имеет начальное значение.О. :Это означает, последовательном
обращении к Random в разных, программах (или при нескольких прогонах одной
программы) будет всегда вь1лапа'оД на и, та же прследовательность псевдослучайных
чисел. НапримёД при; следующём обрабЬтчике bbRunCl.i.ck окно, нашей .учебной
программы будет иметь вид, показанный на рис. 7.2:
procedure
TfinExaniple.bbRunCliak(Sender:TObject);
var
S,3S: String;.
begin
S='';
for
k :=1 to
300 do
SS := IntToStr (Random
(1000))
while
Length(SS)<3
do
if k
mod
2С=0
then
begin
S : = '' ;
end
end
end;
(В программе выводятся 300 псевдослучайных
чисел, которые группируются в строки по 20 чисел и дополняются ведущими нулями,
если число имеет меньше трех цифр.) Если вы захотите повторить программу,
вы получите точно такую же последовательность чисел, что н на рис. 7.2. С
помощью процедуры Randomize в переменную RandSeek помещается
численное значение системного времени,
что привёдет к генерации, другой последовательности. Обращение к этой процедуре
нужно сделать в самом начале обработчика.
Рис. 7.2.
Последовательность
псевдослучайных чисел
Начиная с версии 2 в Delphi включен
модуль Match, который существенно расширяет перечисленный в табл. 7.5 набор
встроенных математических функций. Особенностью реализации содержащихся в нем
почти 70 функций и процедур является их оптимизация для работы с арифметическим
сопроцессором класса Pentium, так что все они производят необходимые вычисления
за рекордно малое время.
Исходный текст содержится в файле
файле Source\Rtl\Sys\Match.pas каталога размещения Delphi. В прил. 3 перечисляются
подпрограммы модуля Match.