Да это - проблема. Но проблема может быть решена с помощью рекордных свойств:
type
TRec = record
private
FA : integer;
FB : string;
procedure SetA(const Value: Integer);
procedure SetB(const Value: string);
public
property A: Integer read FA write SetA;
property B: string read FB write SetB;
end;
procedure TRec.SetA(const Value: Integer);
begin
FA := Value;
end;
procedure TRec.SetB(const Value: string);
begin
FB := Value;
end;
TForm1 = class(TForm)
Button1: TButton;
procedure Button1Click(Sender: TObject);
private
FRec : TRec;
public
property Rec : TRec read FRec write FRec;
end;
procedure TForm1.Button1Click(Sender: TObject);
begin
Rec.A := 21;
Rec.B := 'Hi';
end;
Это компилирует и работает без проблемы.
Я не уверен, что вы имеете в виду под « нормализованное двойное число», но получение следующего представимого двойного числа выполняется с помощью nextafter ()
функция в большинстве стандартных математических библиотек C.
Как указано ниже, после небольшого исследования выясняется, что для положительных чисел с плавающей запятой в формате Intel IEEE754 размером n бит, которые < + бесконечность, обрабатывающая конкатенированную экспоненту и мантиссу как n-1-битовое целое число без знака, добавляя единицу, получаем следующее большее значение и (вычитая единицу, получаем следующее меньшее значение)
И наоборот, если отрицательное. В частности, можно интерпретировать n-1-битовое целое число как представляющее абсолютную величину, не зависящую от знака. И, таким образом, при отрицательном значении необходимо вычесть единицу, чтобы приблизить следующее число с плавающей запятой к нулю после отрицательного числа с плавающей запятой f.
Утверждение в пункте 3) неверно. Если d немного меньше 2, то между d и (1 + eps) * d ровно 1 число с плавающей запятой. Вот программа, которая это демонстрирует:
#include <limits>
#include <iostream>
int main(int, char**)
{
using namespace std;
double d = 1.875;
cout.precision(18);
cout << "d = " << d << "\n";
double d2 = (1.+numeric_limits<double>::epsilon())*d;
cout << "d2 = " << d2 << "\n";
double f = d + (d2-d)/2;
cout << "f = " << f << "\n";
}
Причина в том, что (1 + eps) * 1,875 равно 1,875 + 1,875 * eps, что округляется до 1,875 + 2 * eps. Однако разница между последовательными числами с плавающей запятой между 1 и 2 составляет eps, поэтому существует одно число с плавающей запятой между 1,875 и 1,875 + 2 * eps, а именно 1,875 + eps.
Утверждение в пункте 2) верно, Я думаю. И Роберт Керн, вероятно, ответил на ваш настоящий вопрос.
Я думаю, это будет выпущен, когда он будет готов. Я не знаю даты релиза. Следите за блогом Riding Rails . Записки Райана удобны для отслеживания Edge Rails.
double x = 1.0;
uint64_t rep;
assert(sizeof x == sizeof rep);
memcpy(&rep, &x, sizeof x);
rep += 1;
memcpy(&x, &rep, sizeof x);
Это добавляет единицу к значимости x, работая с поразрядным представлением значения с плавающей запятой; если следующее значение находится в следующем бинаде, оно будет перенесено в показатель степени, вернув правильное значение. Если вы хотите, чтобы он работал с отрицательными значениями, вам нужно это настроить.