Отформатируйте число как валюту в Azure Data Explorer

У меня есть запрос, который возвращает десятичное значение. Я ищу способ отформатировать значение в валюте. Мой текущий вариант использования ограничен долларами США, но я уверен, что другие ищут аналогичные решения.

Я хотел бы иметь возможность перейти от "123456,789" до "123 456,79 $".

3 ответа

Решение

В обозревателе данных Azure отсутствует тип данных валюты. Это генерирует значение, которое вы описываете, но заканчивается строкой, которая, вероятно, не то, что вы хотите.

print Value=123456.789
| extend Currency = round(Value, 2)
| extend Decimal = round(Currency % 1, 2)
| extend WholeNumber = toint(Currency)
| extend Segment4 = WholeNumber / 1000000000 % 1000
| extend Segment3 = WholeNumber / 1000000 % 1000
| extend Segment2 = WholeNumber / 1000 % 1000
| extend Segment1 = WholeNumber % 1000
| project CurrencyString = 
    strcat(
        '$',
        iff(Segment4 > 0, strcat(tostring(Segment4), ','), ''),
        iff(Segment3 > 0, strcat(tostring(Segment3), ','), ''),
        iff(Segment2 > 0, strcat(tostring(Segment2), ','), ''),
        iff(Segment1 > 0, tostring(Segment1), ''),
        substring(Decimal, 1))

Команда принимает запросы функций на https://feedback.azure.com/forums/915733-azure-data-explorer

[Обновлено для обработки запятых для чисел... но все еще имеет множество недостатков / ограничений.]

Я создал функцию, которая поможет в этом:

let currencyFormat = (number: real, symbol: string = "", separator: string = " ") {
    //Convert number to string with 2 decimal places. 
    let StringNum = tostring(round(number, 2));
    //Get the index of the .
    let indexOfDot = indexof(StringNum, ".");
    //Get the number without decimals
    let Num = iif(indexOfDot > -1, substring(StringNum, 0, indexOfDot), StringNum);
    //Get the decimal without number (includes .)
    let Decimal = iif(indexOfDot > -1, substring(StringNum, indexOfDot), "");
    //If decimal only has 1 character, add a 0 afterwards.
    let DecimalFinal = iif(strlen(Decimal) == 2, strcat(Decimal, "0"), Decimal);
    //Get the length of the Number part
    let len = strlen(Num);
    //Get the segments divided into 1000s
    let seg1 = iif(len >= 3, substring(Num, len - 3, 3), Num);
    let seg2 = iif(len >= 6, substring(Num, len - 6, 3), substring(Num, 0, len - 3));
    let seg3 = iif(len >= 9, substring(Num, len - 9, 3), substring(Num, 0, len - 6));
    let seg4 = iif(len >= 12, substring(Num, len - 12, 3), substring(Num, 0, len - 9));
    let seg5 = iif(len >= 15, substring(Num, len - 15, 3), substring(Num, 0, len - 12));
    //Output the final value
    strcat(
        symbol,
        iif(strlen(seg5) > 0, strcat(seg5, separator), ""),
        iif(strlen(seg4) > 0, strcat(seg4, separator), ""),
        iif(strlen(seg3) > 0, strcat(seg3, separator), ""),
        iif(strlen(seg2) > 0, strcat(seg2, separator), ""),
        seg1,
        DecimalFinal
    )
};

Используйте это так:

let currencyFormat = (number: real, symbol: string = "", separator: string = " ") { 
    let StringNum = tostring(round(number, 2));
    let indexOfDot = indexof(StringNum, ".");
    let Num = iif(indexOfDot > -1, substring(StringNum, 0, indexOfDot), StringNum);
    let Decimal = iif(indexOfDot > -1, substring(StringNum, indexOfDot), "");
    let DecimalFinal = iif(strlen(Decimal) == 2, strcat(Decimal, "0"), Decimal);
    let len = strlen(Num);
    let seg1 = iif(len >= 3, substring(Num, len - 3, 3), Num);
    let seg2 = iif(len >= 6, substring(Num, len - 6, 3), substring(Num, 0, len - 3));
    let seg3 = iif(len >= 9, substring(Num, len - 9, 3), substring(Num, 0, len - 6));
    let seg4 = iif(len >= 12, substring(Num, len - 12, 3), substring(Num, 0, len - 9));
    let seg5 = iif(len >= 15, substring(Num, len - 15, 3), substring(Num, 0, len - 12));
    strcat(
        symbol,
        iif(strlen(seg5) > 0, strcat(seg5, separator), ""),
        iif(strlen(seg4) > 0, strcat(seg4, separator), ""),
        iif(strlen(seg3) > 0, strcat(seg3, separator), ""),
        iif(strlen(seg2) > 0, strcat(seg2, separator), ""),
        seg1,
        DecimalFinal
    )
};
MySource
| where Currency1 > 0
| project Currency1 = currencyFormat(Currency1, "$", ","),
          Currency2 = currencyFormat(Currency2, "R", ","),
          Currency3 = currencyFormat(Currency3)

ВХОД:

Currency1 = 1254.3
Currency2 = 13231.02
Currency3 = 4213

ВЫХОД:

 Currency1 | Currency2  | Currency3
-----------|------------|-----------
 $1,254.30 | R13,231.02 | 4 213.00

Другая реализация. Поддерживает отрицательные суммы (-123,45 доллара США) и всегда две цифры для центов (123,00 доллара США).

      let ToFormattedCurrency = (value:decimal ) 
{
    let DecimalString = tostring( round( value, 2 ) );
    let Sign = iff( DecimalString startswith "-", "-","");
    let DollarsString = substring( DecimalString, 0, indexof(DecimalString, "." ) );
    let CentsString = strcat(substring(DecimalString, indexof(DecimalString, "." )), "00"); //pad with extra 00 to force 2 digits, will remove later
    let AbsDollarsString = iff( DollarsString startswith "-", substring(DollarsString,1),DollarsString);
    let AbsDollarsReversedString = reverse(AbsDollarsString);
    let AbsDollarsReversedStringLen = strlen(AbsDollarsReversedString);
    let _hundreds = substring( AbsDollarsReversedString, 0, 3 );
    let _thoundsands = iff( AbsDollarsReversedStringLen > 3,  strcat( _hundreds, ",", substring( AbsDollarsReversedString, 3, 3 ) ), _hundreds );
    let _millions = iff( AbsDollarsReversedStringLen > 6,  strcat( _thoundsands, ",", substring( AbsDollarsReversedString, 6, 3 ) ), _thoundsands ); 
    let _billions = iff( AbsDollarsReversedStringLen > 9,  strcat( _millions, ",", substring( AbsDollarsReversedString, 9, 3 ) ), _millions );
    let FormattedDollarReverse = iff( AbsDollarsReversedStringLen > 12,  strcat( _billions, ",", substring( AbsDollarsReversedString, 12, 3 ) ), _billions );
    strcat("$",Sign,reverse(FormattedDollarReverse), substring( CentsString, indexof( CentsString,".", 0), 3) )
};
Другие вопросы по тегам