Тема / Topic: Сохранение в Базу Данных дробных чисел
Gennady
Junior Member / Новичок
Участник № / Member № 6305
отправлено / posted
Доброго дня!
Уважаемая поддержка, я столкнулся со странной проблемой не точного сохранения в БД дробных значений. Не могу понять почему так происходит. Если в среде разработки IDE TM6 в настройках связи с СУБД я к аргументам устанавливаю значения по умолчанию дробное число с точностью до 5 знаков после запятой. Нажимаю кнопку RUN для запроса. То в БД записывает всё точно и правильно.
Но если к выходным аргументам программы установлю константы, также дробные числа до 5 знаков после запятой. Запускаю профайлер или RTM. Делаю запрос на запись через кнопку которая шлёт номер запроса на входное значение БД. То по непонятной мне причине в БД записывает только целую часть значения!
Тип данных везде LREAL. И обычная привязка выходных аргументов с входными аргументами БД.
Вопрос: Почему так происходит и как это можно исправить?
Gennady
Junior Member / Новичок
Участник № / Member № 6305
отправлено / posted
У меня используется старая версия 6.09. Постараюсь потестить в версии 6.10.2
Но я заметил закономерность что значения между каналами, экранами, программами передаются через привязки корректно а в БД сохраняет только 6 разрядов значений. Пример:
Если в аргументе значение: 1.12345 То в БД запишет: 1.12345 т. е. всё правильно!
Но если в аргументе: 12.12345 БД запишет:12.12350 т.е. 4й разряд после точки округлиться а 5й станет 0
Если в аргументе:123.12345 То в БД запишет:123.12300
Аргумент:1234.12345 В БД:1234.12000
Аргумент:12345.12345 В БД:12345.10000
Аргумент:123456.12345 В БД:123456.00000
Т. е. проблемы с точками и запятыми никакой нет. В БД записывает только 6 первых разрядов. Хотя через IDE TM6 в настройках связи с СУБД если к аргументам установить значения по умолчанию и нажать человечка Аргумент:123456.12345 В БД так же запишет:123456.12345
Сообщения / Posts 27 | Из / From: Россия
| IP / IP: IP адрес / IP address |
Nico
Forum Professor / Завсегдатай форума
Участник № / Member № 5342
отправлено / posted
У чисел с плавающей точкой есть мантисса (целое число фиксированной длины). Для Float (4 байта) мантисса имеет длину 23 бита. Максимально возможное значение мантиссы 2^23 = 8 388 608 Семь значащих символов.
В Вашем примере 12.12345 - семь значащих знаков. Если Вы "увеличиваете" целую часть на 1 знак, то "уменьшится" количество значащих знаков после разделителя на 1. Если формат указан как "отображать 5 знаков после запятой", то допишутся нули. 123.12340 - 7 значащих 1234.12300 - 7 значащих 12345.12000 - 7 значащих
Таким образом, при работе с float (4 байта) получить больше 7 значащих чисел нельзя.
отправлено / posted
Верно. Канал вызова шаблона Программы (аргумент OUT, без привязки) - канал DFloat (привязка к атрибуту канала вызова шаблона Программы, начиная со 140) - Канал Call.SQLQuery (привязка к Реальному значению канала DFloat)
отправлено / posted
Канал Call с типом вызова SQLQuery. Он создается автоматически, как только Вы перенесете шаблон связи с СУБД в Узел.
Сообщения / Posts 17316 | Из / From: Россия
| IP / IP: IP адрес / IP address |
Gennady
Junior Member / Новичок
Участник № / Member № 6305
отправлено / posted
Добрый день техподдержка!
Сделал как вы написали а именно: 1) Создал канал DFloat. 2) На вход канала DFloat привязал к атрибут программы 140 (ARG00) 3) ARG00 канала Call.SQLQuery привязал к реальному значению канала DFloat
Сейчас да в БД пишет числа с точностью Double Float. Но только ОДИН! аргумент.
У меня в программе несколько десятков аргументов нужно передать для записи в разные БД по 16 аргументов на каждую БД с точностью Double Float.
Вопрос: Мне что нужно для каждого аргумента создавать отдельный канал DFloat?