31.08.2017, 13:40 | #1 |
Участник
|
Преобразование к и из строк
У меня еще один быстрый вопрос, возможно кто-то знает ответ сразу, чтоб мне не пришлось экспериментировать.
Мне нужно преобразовать две переменные в строки, а потом назад Нужно гарантировать, что это будет допустимо, то есть чтобы формат в строковом виде был неважен. Какие методы стоит использовать? X++: utcDateTime variable1; // какое-то значение Qty variable2; // какое-то значение str var1Str = datetime2str(variable1); str var2Str = num2str(variable2, -1, -1, -1, -1); utcDateTime variable1_new = str2Datetime(var1Str); Qty variable2_new = str2Num(var2Str); Спасибо |
|
31.08.2017, 13:50 | #2 |
Участник
|
В общем случае это невозможно, так как тип переменных может быть такой, что их невозможно серилизовать. То есть в задаче должны быть какие-то ограничения. Можешь посмотреть как сейчас происходит обработка SysLastValue - там при определенном флаге все фигачится в XML.
Надо понять 1) какие типы ты собираешься преобразовывать, а какие нет 2) Какие требования к получившейся строке Стандартные преобразования для XML есть в XMLCOnvert |
|
31.08.2017, 14:15 | #3 |
Участник
|
Практически любой тип можно преобразовать в строку простой операцией:
X++: s = strFmt("%1", value);
__________________
// no comments |
|
31.08.2017, 14:17 | #4 |
Участник
|
Мне нужно только utcDateTime и real, как указано в примере.
Другие типы не интересуют |
|
31.08.2017, 15:18 | #5 |
Участник
|
Иван, для real не прокатит
Вот такая константа 12345.789012345 усекается дробная часть. Т.е. var2Str = '12 345.79' А variable2_new - вообще равно 12 Проявился старый баг str2Num() Последний раз редактировалось Logger; 31.08.2017 в 15:20. |
|
31.08.2017, 15:24 | #6 |
Участник
|
Похоже, что для utcDateTime лучше всего
X++: DateTimeUtil::toStr() && DateTimeUtil::parse() X++: num2str(value, -1, numOfDec(value), DecimalsSeparator::Dot, ThousandsSeparator::Comma); str2num(); |
|
|
За это сообщение автора поблагодарили: Logger (3). |
31.08.2017, 15:28 | #7 |
Участник
|
Ну дык я потому и спрашиваю, какие функции использовать, чтоб правильные результат был. В примере заведомо неверно
|
|
31.08.2017, 16:53 | #8 |
Участник
|
Цитата:
Container, bin data, Binary, base64 |
|
31.08.2017, 17:42 | #9 |
Участник
|
Ну в принципе да, можно значение завернуть в контейнер, причем не только одно. И не надо заморачиваться с Binary или Base64. И строка в принципе получается очень даже человекочитаемой (для real и utcdatetime, другие типы смотреть надо, экспериментировать, так сказать).
X++: static void ASmallTest(Args _args) { Qty q, qty = 12345.789012345; utcDateTime d, dt = DateTimeUtil::utcNow(); str s = con2str([qty, dt]); ; [q, d] = str2con(s); info(strfmt("%1, %2", qty, dt)); info(strfmt("%1, %2", q, d)); }
__________________
// no comments |
|
|
За это сообщение автора поблагодарили: mazzy (2), trud (3). |
31.08.2017, 17:52 | #10 |
Модератор
|
Как Максим уже писал, можно посмотреть как сериализуются SysLastValue начиная с PU9
X++: public static void main(Args _args) { real myRealValue = 12345.789012345; utcdatetime myUtc = DateTimeUtil::utcNow(); str serializedStr = ContainerHelper::serialize([myRealValue, myUtc]); [myRealValue, myUtc] = ContainerHelper::deserialize(serializedStr); }
__________________
-ТСЯ или -ТЬСЯ ? |
|
|
За это сообщение автора поблагодарили: mazzy (2), trud (3). |
31.08.2017, 18:27 | #11 |
Участник
|
Я бы использовал XMLConvert и разделитель. Например |. Так как XMLConvert расчитан на преобразование туда и сюда
|
|
|
За это сообщение автора поблагодарили: Vadik (1), mazzy (2), gl00mie (1). |
13.09.2017, 09:06 | #12 |
Участник
|
Цитата:
X++: info(new SqlSystem().sqlLiteral(DateTimeUtil::utcNow())); info(new SqlSystem().sqlLiteral("Robert'); DROP TABLE Students;--")); info(new SqlSystem().sqlLiteral(-1234.567890123)); Цитата:
'1900-01-01T00:00:00'
N'Robert''); DROP TABLE Students;--' -1.234567890123E3 Цитата:
anytype хоть и зовётся any, но на самом деле он запоминает тип после первого присвоения. Последующие попытки присвоения запустят штатный механизм преобразований между типами. str же преобразуется почти во всё, кроме DateTime, к сожалению X++: str typeBinding; anytype any = typeBinding; transDate transDate = today(), transDateTest; real realNum = -12345.789012345, realNumTest; int64 i64 = 12345678901234567, i64Test; NoYes enum = NoYes::Yes, enumTest; UtcDateTime dateTime = DateTimeUtil::utcNow(), dateTimeTest; ; Debug::assert(typeof(any) == Types::String); any = transDate; transDateTest = any; Debug::assert(transDateTest == transDate); any = realNum; realNumTest = any; Debug::assert(realNumTest == realNum); any = i64; i64Test = any; Debug::assert(i64Test == i64); any = enum; enumTest = any; Debug::assert(enumTest == enum); any = dateTime; dateTimeTest = any; info("OK"); |
|
13.09.2017, 19:55 | #13 |
Участник
|
Привет, Андрей.
Речь идет о сериализации, чтобы быстро конвертнуть туда и обратно, а не о преобразовании в формат для T-SQL. А с экранизацией спецсимволов SysQuery::value() вполне себе справляется. any2str, str2any подходит, только если в any был записан тип str. По другим типам выскочит ошибка. Если у нас enum, int или UtcDateTime, то о какой конвертации через any2str может идти речь?
__________________
// no comments |
|
14.09.2017, 02:38 | #14 |
Участник
|
|
|
14.09.2017, 11:33 | #15 |
Участник
|
Цитата:
Ещё раз. Примитивные типы могут быть преобразованы в строку одинаковой конструкцией anytype any = ""; any = transDate;. Ошибка не выскочит. Обртаное преобразование не зависит от типа и выглядит transDate = any;, где any - строка, полученная образом выше. Ошибка не выскочит. Исключение составляет лишь упрямый DateTime(в упомянутом con2str кстати на ax2009 та же ерунда и из-за того-же преобразования), но для него есть DateTimeUtil. |
|
14.09.2017, 11:36 | #16 |
Участник
|
в таком случае выскакивала, вроде.
в anytype можно положить значение любого типа пока она не инициализирована. после инициализации переменная получает вполне конкретный тип. и сменить тип уже не получится. |
|
14.09.2017, 11:38 | #17 |
Участник
|
Подобное поведение реализует SysAnyType.
За счет боксинга значения в map |
|
|
|