Использовать круглые скобки абсолютно везде не всегда возможно.
На мой взгляд это не совсем логично поведение преобразования. Т.е. я сначала принудительно преобразую переменную в double, а потом она преобразуется в строку с округлением. Почему парсер решает что мне нужно ее округлить?
У меня есть некий класс DBField, который хранит тип переменной и у него есть метод ^field.init[$value], который возвращает значение. Т.к. он универсален и используется как
Так вы почитайте в доке про double.format - там все описано....
Если не задавать предобразование, то парсер неявно использует %g, что и приводит к кажущимся проблемам. Если хотите предсказуемого результата, то используйте круглые скобки. [Ну и почитать про то как работают числа с плавающей точкой не помешает — я вам раньше давал ссылку на википедию.]
В примере Sumo там будет объект field. Как объект реализует хранение значений внутри себя — его личное дело. И вы на это можете влиять напрямую, написав нужную логику хранения.
DBField хранит только мета информацию о свойстве. ^field.init[$value] - возвращает значение свойства (в типах парсера) полученное из $value. И тип он хранит в объекте DBField, поэтому проблемы с преобразованием не возникает. А вот с дальнейшим присвоением уже и возникает потеря значений.
Из-за логики преобразований парсером из double в строку пришлось преобразовывать в double, форматировать в строку и возвращать строку.
Как понимаю, другого решения не возможно на текущий момент.
double -- это штука чуть более хитрая, чем вы её себе представляете, судя по этому: Странный формат - если 5000.66, то получу при преобразовании к строке 5000.66, а если 15000.66, то получу 15000.7
Каким образом парсер так решает?
задание double в виде $var(1.23) -- это лишь частный случай. есть ещё такой способ задания: $var(1/3) а посре прочтения сообщения PAF-а вы, я надеюсь, поймёте, что после выполнения $f(123.86-123) при выводе полученного double без округления будет выведено совсем не "0.86"
Проблема возникает не в том, что я забываю привести double к нужному формату, а в:
1. Изначально я знаю тип переменной 2. По ходу кода у меня есть $value и я уже не знаю (и с первого взгляда мне это не важно) тип переменной. 3. Но т.к. я делаю присвоение переменной через [] всегда, то получается что я теряю значение.
Т.е. получается, что если у меня есть $value и я не знаю что это и какие скобки ставить, то при вызове какого-нибудь метода или присвоения другой переменной я теряю ее тип.
Последние 2 строки кода теряют значение в double. Добавлять при присвоении switch по типу выглядит не разумно.
Получается выхода два: 1. При работе с double в моем коде всегда делать $value[^sData.format[%f]] или с большим количеством знаков Но при таком подходе при вызове без формата у меня всегда будет куча нулей.
вообще-то изначально вы написали: Итого мы получаем, что при преобразовании числа в double (см. 4 и 5) мы теряем правильное значение. Это ошибка или так задумывалось?
соотв. вам объяснили, почему при печати чисел происходит округление.
сейчас вы говорите про другой момент, который к сожалению присутствует. увы, при передачи чисел в квадратных скобках происходит их "печать" с соотв. последствиями. сделать иначе не получится, т.к. простой вывод в output -- это тоже печать, и тут число должно преобразовываться в строку.
думаю, вы можете "родить" свой класс Double, который решит всё проблемы. единственное -- красивого конструктора не получится.
Тип я знаю всегда, но я стараюсь при получении данных из "вне" (форма, БД) преобразовать его к типу Парсера. И т.к. при возврат значения происходит в методе объекта, который знает тип, а сохранение в массив происходит в классе, которые не знает типа, то и возникла вышеописанная проблема.