2013-10-14 2 views
1

У меня есть таблица Oracle с столбцом типа NUMBER, который содержит ряд чисел с плавающей запятой. Что такое правильный способ чтения, что в переменную C помощью Pro * C Я пробовал следующее:Обработка плавающих чисел в Pro * C

EXEC SQL BEGIN DECLARE SECTION; 
static float o_start_x; 
EXEC SQL END DECLARE SECTION; 

EXEC SQL SELECT start_x 
FROM my_table 
INTO :o_start_x; 

чаще, что это не нормально, однако некоторые числа с плавающей точкой, в частности, очень близко к 0 (например, 1.4E-43) вызывает следующие ошибки:

ORA-01426: numeric overflow; 

есть ли правильный/безопасный способ чтения такого значения, или метода, имеющий оракул преобразовать тип достаточно безопасно, позволяя потерю точности ?

ответ

2

Поплавок допускает ограниченную точность - у двойного больше 15 цифр.

Опасность: с плавающей точкой возникают проблемы при работе с деньгами, например. Пример: .10 не может быть точно представлен в внутреннем представлении данных с плавающей точкой IEEE-754. Общим обходным решением является использование арифметики BCD, которая позволяет избежать проблем с плавающей запятой, а затем читать окончательный результат в двойном.

FLT_DIG 
This is the number of decimal digits of precision for the float data type. Technically, if p and b are the precision and base (respectively) for the representation, then the decimal precision q is the maximum number of decimal digits such that any floating point number with q base 10 digits can be rounded to a floating point number with p base b digits and back again, without change to the q decimal digits. 

FLT_DIG обычно шесть цифр точности минимум DBL_DIG: 15.

Пока вы не делать много математики и сравнивает в коде C, если вы не знаете, как справиться с проблемами, которые я упомянул и другие вопросы, получение окончательного результата за деньги легко.

EXEC SQL BEGIN DECLARE SECTION; 
static double o_start_x; 
EXEC SQL END DECLARE SECTION; 

EXEC SQL SELECT start_x 
FROM my_table 
INTO :o_start_x; 

Если это число является гигантским, возможно, вам придется использовать строку. Предел для NUMBER - 32 цифры точности, что превышает пределы точности для общих типов данных C. Pro * C не поддерживает бинарные типы данных AFAIK.

+0

'.10' _can_ быть точно представленным в IEEE-754 decimal32, decimal64 и decimal128. '.10' _cannot_ быть точно представлены в двоичных файлах IEEE-754, binary32, binary64 и binary128. Бинарные форматы более распространены. – chux

+0

Вы правы, decimalnnn обычно не используется в аппаратных средствах. Можете ли вы назвать товарное оборудование, которое у него есть? Я не могу. Мейнфрейм делает. Смотрите: http://stackoverflow.com/questions/1447215/why-arent-floating-point-decimal-numbers-hardware-accelerated-like-floating-poi –

+0

Мой комментарий не был направлен на аппаратное обеспечение, а просто на идею IEEE -754 и '0,1'. Существует несколько вариантов реализации десятичной библиотеки. В Google-decimal64 появилось несколько из них. Поскольку система Oracle, вероятно, может потребовать быструю десятичную реализацию (т. Е. HW), ваше утверждение, скорее всего, будет правильным в рамках этой статьи, о которой думают не в целом. «Можете ли вы назвать товарное оборудование ...» звучит как хороший вопрос для публикации, поскольку 4-летняя ссылка, которую вы дали, может пригодиться с информацией 2013 года. – chux

Смежные вопросы