Форум: "Начинающим";
Текущий архив: 2006.07.30;
Скачать: [xml.tar.bz2];
ВнизКак преобразовать 48-битное число? Найти похожие ветки
← →
Zilog © (2006-07-04 14:30) [0]Как преобразовать 48-битное число? При том, что мантисса кодируется 36-ю битами, а экпонента 12-ю.
например, вот это число равно еденице (1): 70368744179712
а вот это минус еденице (-1): -140737488353281
← →
MBo © (2006-07-04 14:36) [1]Во что преобразовать?
Где знак кодируется?
Что идет сначала - мантисcа или экспонента?
Экспонента смещенная или нет?
Как нормализована мантисса?
← →
Zilog © (2006-07-04 14:51) [2]Numerical Values
PMAC can store and process numerical values in many forms, with both fixed-point and floating-point values. The Motorola 56000 DSP that acts as the PMAC CPU is a fixed-point processor with built-in 24- bit and 48-bit arithmetic capability (plus a 56-bit accumulator). However, the PMAC firmware implements a full set of floating-point routines.
Internal Formats
The internal servo, interpolation, and commutation routines all operate with fixed-point arithmetic, 24-bit and 48-bit, for maximum speed. The user motion and PLC programs, use floating-point arithmetic for maximum range and generality. Even when reading from and/or writing to fixed-point registers, the intermediate formats are all floating-point values. The only exception to this rule is the new compiled PLC programs; in a statement containing only L-variables and integer constants, the intermediate format is signed 24-bit integer. Refer to the section on compiled PLCs under the Writing a PLC Program section of this manual for more details. The general floating-point format is 48 bits long, with a 36-bit mantissa and a 12-bit exponent. This provides a range of +2+2047, or +3.233 x 10+616, which should provide sufficient range for any foreseeable
uses on the card.
Receiving Values
Constant values sent from the host as part of command lines are sent as ASCII text, either as decimal values or hexadecimal values. Hexadecimal values must be preceded by a $ character; they must be
unsigned, and they cannot include fractional values. Decimal values can be positive or negative, and can include fractional values. The PMAC value interpreter does not support exponential notation, and it is limited to passing through values in the range +2+35, or +3.43 x 10+10. Values outside this range are truncated to the maximum or minimum values of the range.
Этой информации достаточно?
← →
MBo © (2006-07-04 15:33) [3]>Этой информации достаточно?
нет
← →
MBo © (2006-07-04 15:42) [4]первое число в Hex
400000000800
второе
8000000007FF
Так что пока непонятно...
← →
tsa (2006-07-04 15:44) [5]Zilog © (04.07.06 14:30)
смотри крайние значения, анализируй
если адрес такой переменной знаешь, то грузи частями мантису/порядок
в asm вставке
← →
Zilog © (2006-07-04 16:50) [6]>>MBo © (04.07.06 14:36) [1]
1) преобразовать в "человеческий" вид. ЧТо бы можно было отобразить читабельное число, а не набор цифр.
2) подозреваю, что в 40-ом бите
3) Судя по международному стандарту, расклад такой:
Знак (48 бит), Экспонента(47..37), Мантисса(36..0)
4) неизвестно, но скорее всего оно не нормализовано, т.е. окажется вида 1234.567, например.
← →
MBo © (2006-07-04 16:57) [7]Ну тогда давай больше чисел, и лучше сразу в hex, например, из набора:
0 0.25 0.5 0.75 2 3 4 5 100 1048576
-2 -3 -0.5
← →
Zilog © (2006-07-04 17:52) [8]пожалуйста:
0.25 = 4000000007FE
0.5 = 4000000007FF
0.75 = 6000000007FF
2 = 400000000801
3 = 600000000801
4 = 400000000802
5 = 500000000802
100 = 640000000806
1048576 = 400000000814
-2 = 800000000800
-3 = A00000000801
-0.5 = 8000000007FE
← →
Zilog © (2006-07-05 09:56) [9]up
← →
MBo © (2006-07-05 11:23) [10]Вот это проходит, кроме числа -3
procedure TForm5.Button1Click(Sender: TObject);
var
i64, M: Int64;
e: SmallInt;
x: Double;
Sign : Integer;
begin
i64 := StrToInt64("$" + Edit1.Text);
M := i64 shr 12;
Sign := 1;
if (M and $800000000) <> 0 then begin
M := M - $400000000;
Sign := - 1;
e:= (i64 and $FFF) - $7FF - 34;
end else
e:= (i64 and $FFF) - $800 - 34;
x := Sign * M * Power(2, e);
Label1.Caption := Format("%x %d %f",[M, e, x]);
end;
← →
Zilog © (2006-07-05 11:28) [11]>>Power(2, e);
Power - это что?
← →
MBo © (2006-07-05 11:30) [12]uses math
← →
Zilog © (2006-07-05 11:44) [13]даа... с отрицательными числами вообще беда какая-то...
эх. надо было в математику лучше учить... :)
вот это может помочь делу?
http://www.quadibloc.com/comp/cp02.htm
← →
MBo © (2006-07-05 11:47) [14]>даа... с отрицательными числами вообще беда какая-то...
еще несколько отрицательных покажи
← →
Zilog © (2006-07-05 11:59) [15]99999999A7FC -0.1
AA19C47747E5 -0.00000001
8000000007FF -1
B97247454800 -1.1024
A00000000800 -1.5
800000000800 -2
B00000000801 -2.5
9C0000000806 -100
82DCCBFB1809 -1001.1001
800000000809 -1024
80000000080B -4096
BFFF9999A80C -4096.1
80000000080D -16384
BFFFFFF9780E -16384.0001
8A432EAE081A -123456789.123456789
← →
MBo © (2006-07-05 12:18) [16]Теперь понятно, это дополнительный код.
procedure TForm5.Button1Click(Sender: TObject);
var
i64, M: Int64;
e: SmallInt;
x: Double;
begin
i64 := StrToInt64("$" + Edit1.Text);
M := i64 shr 12;
if (M and $800000000) <> 0 then
M := -((not M) and $FFFFFFFFF) - 1;
e:= (i64 and $FFF) - $800 - 34;
x := M * Power(2, e);
Label1.Caption := Format("%f",[x]);
end;
← →
Zilog © (2006-07-05 12:20) [17]>>MBo © (05.07.06 11:23) [10]
глючит форматирование числа:
если ввести положительное число 499602D2281E, на выходе получаем "499602D22 -4 1234567890,13".
перед форматированием числа значение показывает верное - х=1234567890,1
---
приятель тоже копает, говорит преобразование выполняется с помощью логарифмов - чуть позже выложу то, что он накопал.
← →
MBo © (2006-07-05 12:25) [18]Верное число - 1234567890,125
← →
Zilog © (2006-07-05 12:26) [19]>>MBo © (05.07.06 12:18) [16]
Работает лучше. Спасибо большое.
Еджинственное:
1) часто добавляет ненужный ноль, например:
-0,10 (99999999A7FC)
-4096,10 (BFFF9999A80C)
2) Не до конца переводит число, например:
исходное -16384.0001 (BFFFFFF9780E) превращает в -16384,00
← →
MBo © (2006-07-05 12:30) [20]>[19]
Это не имеет отношения к самому числу, а лишь к его строковому представлению, так ты почитай про format strings - я самое простое поставил, где два знака выводится
Label1.Caption := Format("%13.8f", [x]);
← →
Zilog © (2006-07-05 15:42) [21]Большое спасибо! Все вроде работает!
А можно комментарии к алгоритму? Да бы понять суть происходящего.
← →
Zilog © (2006-07-05 16:12) [22]// получаем мантиссу и знак
M := i64 shr 12;
// смотрим, отрицательное ли число?
//если отрицательное, инвертируем мантиссу и убираем знак
if (M and $800000000) <> 0 then M := -((not M) and $FFFFFFFFF) - 1;
//вычисляем экспоненту (почему так - непонимаю)
e:= (i64 and $FFF) - $800 - 34;
//эта строчка мне тоже непонятна
x := M * Power(2, e);
2MBo: Поправь меня, если не сложно
И еще - а обратно как? из строчки вида "0.0001" как получить 48-битное число?
← →
MBo © (2006-07-05 16:16) [23]>А можно комментарии к алгоритму?
да вроде там все должно быть ясно...
M := i64 shr 12;
//извлекается мантисса M - 36 разрядов
if (M and $800000000) <> 0 then
M := -((not M) and $FFFFFFFFF) - 1;
//если установлен старший бит - значит, число отрицательное, получаем его абсолютное значение - для дополнительного кода это делается инверсией битов с прибавлением единицы, затем - добавляем. Если бы это было полное значение 32 или 64 разряда, этого бы не потребовалось, доп. код и так бы правильно интерпретировался
e:= (i64 and $FFF) - $800 - 34;
//выделяем младшие 12 бит, экспонента смещенная - вычитаем $800, и 34 - для нормализации мантиссы
x := M * Power(2, e);
//x :=M*2^e
← →
MBo © (2006-07-05 16:22) [24]>затем - добавляем
должно быть -
затем меняем знак
← →
Zilog © (2006-07-05 16:27) [25]А как ты узанл, смещенная ли мантисса, и на сколько она смещена? Т.е. откуда цифра $800.
И то же самое с нормализацией - откуда 34?
Извини, если вопросы глупые.
← →
MBo © (2006-07-05 16:57) [26]>А как ты узанл, смещенная ли мантисса, и на сколько она смещена? Т.е. откуда цифра $800
Во внутреннем формате IEEE 754 Single и Double экспонента тоже смещенная.
http://en.wikipedia.org/wiki/IEEE_floating-point_standard
А из предоставленных чисел видно - для числа 1 экспонента $800 соответствует 1, т.е. 2 в нулевой степени
мантисса $400000000 - 36 разрядов нормализуется до единицы делением на 2^36 и (почему-то) умножением на 4 = 2^2, отсюда 36-2=34
(можно рассматривать и так, что мантисса нормализована на интервал [4..8), в отличие от IEEE стандарта [1..2) )
← →
Zilog © (2006-07-06 10:22) [27]что то никак не получается сделать обратное преобразование... :(
MBo, не поможешь?...
← →
Zilog © (2006-07-06 14:51) [28]up
MBo, спасай!
← →
Zilog © (2006-07-06 14:54) [29]up
MBo, спасай!
← →
MBo © (2006-07-06 15:24) [30]Для отрицательных чисел-степеней двойки (-0.5, -1, -2, -4) степень смещена на единицу, но фактическое число то же самое, а подгонять лень.
procedure TForm5.Button2Click(Sender: TObject);
var
i64, M: Int64;
e: SmallInt;
x, y, z, Man: Double;
begin
try
x := StrToFloat(Edit2.Text);
except
x := 0;
Edit2.Text :="0";
end;
if x<>0 then
e := Trunc(Log2(Abs(x)))
else
e := 0;
M := Trunc(x * Power(2, 34 - e)) and $FFFFFFFFF;
i64 := (M shl 12) or (e + $800);
Edit1.Text := Format("%x",[i64]);
end;
← →
Zilog © (2006-07-06 16:43) [31]>>MBo © (06.07.06 15:24) [30]
спасибо большущее, мастер.
>>но фактическое число то же самое, а подгонять лень.
я погонял некоторые числа туда-обратно, всё с виду отлично.
но при обратной конвертации на выходе число меняется - это мне что и где надо подгонять?
← →
Zilog © (2006-07-07 18:01) [32]MBo!
а вот это число не преобразовывается....
7FFFFF000FFF
вот на этой строчке вылетает ошибка:
x := M * Power(2, e);
не подскажешь как исправить?
← →
Zilog © (2006-07-10 09:43) [33]MBo! Выручай, нихрена не получается у меня с этой математикой... :(
← →
SergP. (2006-07-10 10:44) [34]
> x := M * Power(2, e);
А зачем Power(2,e), если Power(2,e) = 1 shl e
?
← →
Zilog © (2006-07-10 14:13) [35]Народ, может кто-то ещё в этой теме понимает? Очень нужна ваша помощь.
Страницы: 1 вся ветка
Форум: "Начинающим";
Текущий архив: 2006.07.30;
Скачать: [xml.tar.bz2];
Память: 0.53 MB
Время: 0.016 c