In Delphi , utilizzando FloatToStrF
o CurrToStrF
utilizzerà automaticamente il carattere DecimalSeparator
per rappresentare un segno decimale. Purtroppo DecimalSeparator
is declared in SysUtils as Char
1,2:Come convertire float o valuta in una stringa localizzata?
var
DecimalSeparator: Char;
Mentre il LOCALE_SDECIMAL
è permesso di essere fino a tre caratteri: ""
Character (s) utilizzati per il separatore decimale, per esempio, in "3.14" o "," in "3,14". Il numero massimo di caratteri consentiti per questa stringa è quattro, incluso un carattere null che termina.
In questo modo Delphi non riesce a leggere correttamente il separatore decimale; ricadendo di assumere un separatore decimale predefinito di ".
":
DecimalSeparator := GetLocaleChar(DefaultLCID, LOCALE_SDECIMAL, '.');
Sul mio computer, which is quite a character, questa causa valori in virgola mobile e di valuta per essere localizzato in modo non corretto con un segno U+002E (punto) decimale.
i am disposto a chiamare le funzioni API di Windows direttamente, che sono progettati per la conversione in virgola mobile, o la valuta, i valori in una stringa localizzata:
Tranne queste funzioni, prendi una stringa di codici immagine, dove gli unici caratteri consentiti sono:
- caratteri "0" a "9" (
U+0030
..U+0039
) - Un punto decimale (
.
) se il numero è un valore in virgola mobile (U+002E
) - Un segno meno nella prima posizione del carattere se il numero è un valore negativo (
U+002D
)
Quale sarebbe un buon modo per convertire una virgola mobile, o la valuta, valore in una stringa che obbedisce quelli regole? per esempio.
1234567.893332
-1234567
dato che il locale dell'utente locale (cioè il computer):
- non potrebbe utilizzare un
-
per indicare negativo (ad es--
) - might not use a
.
to indicate a decimal point (ad es.,,
- might not use the latin alphabet
to represent digits (ad es.[cifre rimosse arabe che si infrangono parser SO javascript])
un orribile, orribile, hack, che ho potuto usare:
function FloatToLocaleIndependantString(const v: Extended): string;
var
oldDecimalSeparator: Char;
begin
oldDecimalSeparator := SysUtils.DecimalSeparator;
SysUtils.DecimalSeparator := '.'; //Windows formatting functions assume single decimal point
try
Result := FloatToStrF(Value, ffFixed,
18, //Precision: "should be 18 or less for values of type Extended"
9 //Scale 0..18. Sure...9 digits before decimal mark, 9 digits after. Why not
);
finally
SysUtils.DecimalSeparator := oldDecimalSeparator;
end;
end;
Ulteriori informazioni sulla catena di utilizza il VCL:
FloatToStrF
eCurrToStrF
chiamate:FloatToText
chiamate:
Nota
DecimalSeparator: Char
, il singolo character global is deprecated, e sostituito con un altro separatore decimale singolo carattere
nella mia versione di Delphi
e nelle attuali versioni di Delphi
+1 Mi piace sempre leggere le tue domande. –
Di certo possono richiedere molto tempo per scrivere, formattare, collegare, ecc. E in questo caso una precedente iterazione che includeva numeri arabi si schiantò SO. È bello sapere che lo sforzo non è poco apprezzato. –
Sei su delphi5. Da Delphi2007 puoi chiamare con un set separato di impostazioni dei formati per tutte quelle funzioni di formato. È ora di salire? –