Dezimaltrenner (DecimalSeparator) in Lazarus falsch

Für Fragen zur Programmiersprache auf welcher Lazarus aufbaut
Antworten
petwey
Beiträge: 83
Registriert: Sa 24. Nov 2012, 19:00
OS, Lazarus, FPC: Windows10 und Linux 32 und 64Bit (L 2.2.2 FPC 3.2.2)
CPU-Target: 32Bit und 64Bit

Dezimaltrenner (DecimalSeparator) in Lazarus falsch

Beitrag von petwey »

Hallo Forum,

ich hab mich eben sehr gewundert, warum mir Zahlen mit einem PUNKT als Dezimaltrenner ausgeben werden. Ich betreibe ein deutsches Linux mit 64Bit.

Dann hab ich DefaultFormatSettings.DecimalSeparator ausgeben lassen und das steht tatsächlich ein PUNKT drin. Wenn ich OpenOffice Calc öffne dann hab ich hier den korrekten Trenner nämlich KOMMA.

Mir scheint mein Lazarus läuft hier nicht richtig, vielleicht werden die DefaultFormatSettings nicht richtig gesetzt. Ich will nicht die Einstellungen händisch setzen, sondern das die Programme das automatisch tuen.
Wann und wo werden denn die DefaultFormatSettings von Lazarus / FPC eingelesen? Vielleicht kann man hier ansetzen. Ach ja, unter Werkzeuge/Einstellungen/Allgemein hab ich als Sprache "Automatisch (oder Englisch)" und das Lazarus-Menü ist deutsch.

Ich hab nochmal gesucht und die Datei /usr/share/fpcsrc/3.0.0/packages/rtl-extra/src/unix/clocale.pp gefunden in der mit GetFormatSettings(DefaultFormatSettings); eigentlich die DefaultFormatSettings eingelesen werden sollten.
Diese Unit habe ich mit in die uses-Liste eingetragen, danach war schon mal der DezimalSeparator KOMMA aber FloatToStr(13.5) liefert immer noch PUNKT.

Bitte um Hilfe und Danke im voraus.
MfG,
petwey

Windows 10 und Linux 32 und 64Bit (L 2.2.2 FPC 3.2.2)

wp_xyz
Beiträge: 4869
Registriert: Fr 8. Apr 2011, 09:01

Re: Dezimaltrenner (DecimalSeparator) in Lazarus falsch

Beitrag von wp_xyz »

Was kommt den bei "WriteLn(DefaultFormatSettings.DecimalSeparator)"?

Ich denke, du verwendest eine der alten Pascal-Routinen Str oder Val - diese ignorieren den DecimalSeparator. Aber bei den neuen Konvertierungsroutinen, wie FloatToStr, StrToFloat, FormatFloat('0.00', x), Format(''%.2f', [x]), sollte der Decimalseparator richtig sein (es sei denn, du verwendest einen optionalen Parameter FormatSettings, in denen der DecimalSeparator für den Augenblick verändert wird).

Code: Alles auswählen

 
program Project1;
 
{$mode objfpc}{$H+}
 
uses
  SysUtils;
 
var
  s: String;
  fs: TFormatSettings;
 
begin
  WriteLn(1.2);
 
  Str(1.2, s);
  WriteLn(s);
 
  WriteLn(Format('0.00', [1.22]));
  WriteLn(FormatFloat('0.00', 1.2));
 
  WriteLn(DefaultFormatSettings.DecimalSeparator);
 
  fs := DefaultFormatSettings;
  fs.DecimalSeparator := '.';
  WriteLn(FormatFloat('0.00', 1.2, fs));
 
  ReadLn;
end.   


[EDIT]
Ich sehe gerade, du erwähnst Linux. Tatsächlich, da wird auch beim meinem Mint der Dezimaltrenner als Punkt genommen. obwohl unter Regionales das Komma eingetragen ist. Dazu könntest du einen Bugreport schreiben.

petwey
Beiträge: 83
Registriert: Sa 24. Nov 2012, 19:00
OS, Lazarus, FPC: Windows10 und Linux 32 und 64Bit (L 2.2.2 FPC 3.2.2)
CPU-Target: 32Bit und 64Bit

Re: Dezimaltrenner (DecimalSeparator) in Lazarus falsch

Beitrag von petwey »

Hallo wp_xyz,

sehr gut das es nicht nur mir so geht!!

Ich hab noch nie einen Bug gemeldet und stehe sehr unter Stress, könntest Du das Bitte übernehmen :oops:

Mir erscheint erwähnenswert, das durch Einbinden der Unit clocale der Dezimaltrenner in der Struktur DefaultFormatSettings zwar richtig ist aber das direkt danach verwendete FloatToStr scheint nicht auf die selbe Struktur zuzugreifen. Auch Ändern von DefaultFormatSettings.DecimalSeparator und DefaultFormatSettings.ThousandsSeparator bringt nichts.

Aber auf die Schnelle kann ich mir durch ein Workaround helfen.

Nochmals Danke.

[EDIT]
Ich habe gerade mal die Spur durch die Units verfolgt. Angefangen bei Strg+ FloatToStr anklicken UND siehe da ich lande bei uPSutils von Pascalscript. Ich glaube nicht das der das ursprüngliche FloatToStr im Zuge von Pascalscript entstanden ist. Aber ich brauche PascalSript ganz notwendig!

So und nun hatte ich noch eine Idee: Wenn in mehreren Units die gleiche Prozedur enthalten ist welche gewinnt dann - die in der ersten Unit oder die in der zweiten Unit??? Ich hab also nach uPSUtils in meiner uses-Liste gesucht. War ziemlich weit hinten. Hab se ganz nach vorne gesetzt noch vor Classes. Und siehe da jetzt geht's.

Ich hab jetzt eine Lösung, aber der Bug hängt meiner Meinung nach mit Pascalscript zusammen und ist noch nicht endgültig gelöst.
Ein erster Blick auf meine ScriptEngine zeigt noch keine Nachteile.

Wen es interessiert ich kämpfe auch mit Pascalscript (aber nicht erfolglos :? )http://www.lazarusforum.de/viewtopic.php?f=18&t=9603
Zuletzt geändert von petwey am Sa 7. Mai 2016, 19:45, insgesamt 1-mal geändert.
MfG,
petwey

Windows 10 und Linux 32 und 64Bit (L 2.2.2 FPC 3.2.2)

wp_xyz
Beiträge: 4869
Registriert: Fr 8. Apr 2011, 09:01

Re: Dezimaltrenner (DecimalSeparator) in Lazarus falsch

Beitrag von wp_xyz »

Ach natürlich! Du musst nur clocale in Uses einbinden, dann werden die Ländereinstellungen auch unter Linux berücksichtigt, den Bugreport kann man sich sparen. Den Rest deiner Nachricht kann ich nicht bestätigen.

Code: Alles auswählen

program Project1;
 
{$mode objfpc}{$H+}
 
uses
  clocale, sysutils;
 
begin
  WriteLn(DefaultFormatSettings.DecimalSeparator);   // --> ,
  WriteLn(DefaultFormatSettings.ThousandSeparator);  // --> .
  WriteLn(FloatToStr(1.2));   // --> 1,2
  WriteLn(FloatToStr(StrToFloat('1,23')));  // --> 1,23 (Dies funktioniert nur, wenn der Dezimaltrenner ein Komma ist.)
end

petwey
Beiträge: 83
Registriert: Sa 24. Nov 2012, 19:00
OS, Lazarus, FPC: Windows10 und Linux 32 und 64Bit (L 2.2.2 FPC 3.2.2)
CPU-Target: 32Bit und 64Bit

Re: Dezimaltrenner (DecimalSeparator) in Lazarus falsch

Beitrag von petwey »

Hallo wp_xyz,

jetzt haben sich unsere Antworten zeitlich überschnitten. Schau noch mal in den 3. Beitrag.

Gruß petwey
MfG,
petwey

Windows 10 und Linux 32 und 64Bit (L 2.2.2 FPC 3.2.2)

wp_xyz
Beiträge: 4869
Registriert: Fr 8. Apr 2011, 09:01

Re: Dezimaltrenner (DecimalSeparator) in Lazarus falsch

Beitrag von wp_xyz »

petwey hat geschrieben:Wenn in mehreren Units die gleiche Prozedur enthalten ist welche gewinnt dann - die in der ersten Unit oder die in der zweiten Unit??? Ich hab also nach uPSUtils in meiner uses-Liste gesucht. War ziemlich weit hinten. Hab se ganz nach vorne gesetzt noch vor Classes. Und siehe da jetzt geht's.

Erstens kann ich mir immer nie merken, ob die Unit vorne oder am Ende sein muss, und zweitens verliert man bei komplexen Unit-Abhänigkeiten schnell den Überblick, welche Unit zuerst kommt. Daher erscheint es mir besser, in diesen kritischen Fällen den Unitnamen voranzustellen, also

Code: Alles auswählen

  WriteLn(SysUtils.FloatToStr(1.2));

petwey
Beiträge: 83
Registriert: Sa 24. Nov 2012, 19:00
OS, Lazarus, FPC: Windows10 und Linux 32 und 64Bit (L 2.2.2 FPC 3.2.2)
CPU-Target: 32Bit und 64Bit

Re: Dezimaltrenner (DecimalSeparator) in Lazarus falsch

Beitrag von petwey »

Hallo wp_xyz,

das ist ein guter Tip. Noch besser wäre es wenn es zu solchen Überschneidungen gar nicht käme.
Ich denke in Pascalscript muss noch einiges getan werden.
MfG,
petwey

Windows 10 und Linux 32 und 64Bit (L 2.2.2 FPC 3.2.2)

Mathias
Beiträge: 6164
Registriert: Do 2. Jan 2014, 17:21
OS, Lazarus, FPC: Linux (die neusten Trunk)
CPU-Target: 64Bit
Wohnort: Schweiz

Re: Dezimaltrenner (DecimalSeparator) in Lazarus falsch

Beitrag von Mathias »

Der Dezimaltrenner wird wohl immer ein leidiges Thema sein.

Am Computer freundlichsten wird wohl immer der Punkt als Trenner bleiben.

Wer hatte eigentlich dazumal, diese gute Idee, ein Komma als Trenner am PC zu verwenden ?
Wurde dies dazumal mit Windows eingeführt ?

Wir in der Schweiz haben zum Glück einen Punkt als Trenner, so wie es in der USA auch ist.
Obwohl wir auf einem Blatt Papier ein Komma schreiben.

Zum Glück haben auch alle Programmiersprachen einen Punkt.
Das würde sonst recht lustig aussehen:

Code: Alles auswählen

WriteLn(123,456, 123,456);

wen man 2x 123.456 ausgeben will. :mrgreen:
Mit Lazarus sehe ich grün
Mit Java und C/C++ sehe ich rot

wp_xyz
Beiträge: 4869
Registriert: Fr 8. Apr 2011, 09:01

Re: Dezimaltrenner (DecimalSeparator) in Lazarus falsch

Beitrag von wp_xyz »

Da sehe ich jetzt kein Problem, man muss natürlich auch das Listenzeichen anpassen. In Excel gibt man (in Deutschland) Dezimalzahlen mit einem Komma und als Listenzeichen den Strichpunkt ein; dein Beispiel würde in einem imaginären lokalisierten Pascal dann so lauten:

Code: Alles auswählen

  WriteLn(123,456; 123,456); 

Gott-sei-dank haben wir das aber nicht. Lokalisierte Programmiersprachen sind ein Greuel, schon das lokalisierte Excel ("=ZÄHLENWENN(...)" statt "=COUNTIF"(...)).

Aber Progammiersprachen sind die Ausnahme. Jedes (?) andere Programm macht mit lokalisierten Zahleneingaben durchaus Sinn, vor allem wenn es jemand anders verwendet als der Programmierer selber. Das ist das, was die "normalen" Leute in der Schule gelernt haben. Als ich in der Grundschule war (wiegesagt in Deutschland), lernte ich: null-komma-fünf, nicht null-punkt-fünf. Und das war lange bevor es Windows gab. Windows, genauso wie Linux, setzt hier lediglich die Vorgaben eines bestimmten Kulturkreises um.

Aus diesem Grund finde ich Programme, die dem Benutzer einer ungewohnte Schreibweise von Dezimalzahlen, Datumswerten (2016-05-08, oder noch schlimmer die amerikanische Variante 05/08/16) aufzwingen wollen, unprofessionell, und sie haben eine kurze Lebensdauer auf meiner Festplatte.

Delphi, FPC und Lazaraus haben die DefaultFormatSettings, die automatisch mit den jeweiligen Ländereinstellungen vorbelegt werden, und die üblichen Konvertierungsroutinen StrToFloat, FloatToStr, StrToDate, DateToStr usw verwenden diese. Es sei denn, man braucht. z.B. für das Einlesen einer "anderssprachigen" Datei andere Einstellungen. Dann kann man sich die FormatSettings lokal abändern und als zusätzlichen Parameter angeben.

Mathias
Beiträge: 6164
Registriert: Do 2. Jan 2014, 17:21
OS, Lazarus, FPC: Linux (die neusten Trunk)
CPU-Target: 64Bit
Wohnort: Schweiz

Re: Dezimaltrenner (DecimalSeparator) in Lazarus falsch

Beitrag von Mathias »

Lokalisierte Programmiersprachen sind ein Greuel, schon das lokalisierte Excel ("=ZÄHLENWENN(...)" statt "=COUNTIF"(...)).

Ich wollte mal in Excel eine Wurzel ziehen, habe sqr, sqrt probiert, nicht hat funktioniert. Es war ganz einfach WURZEL. :mrgreen:


Das ist das, was die "normalen" Leute in der Schule gelernt haben. Als ich in der Grundschule war (wiegesagt in Deutschland), lernte ich: null-komma-fünf, nicht null-punkt-fünf.

Das ist bei uns in der Schweiz auch so, aber auf dem PC gibt man einen Punkt an.
Das schlimmste an euch finde ich, das ihr den Punkt als Tausender-Teiler brauchen, da finde ich die Darstellung 1'000'000.00 viel besser.
Wen zB. 1.000 steht, heisst dies jetzt Tausend, oder EinsPunktNullNullNull.
Aber dies ist wohl Geschmackssache. :wink:


Delphi, FPC und Lazaraus haben die DefaultFormatSettings, die automatisch mit den jeweiligen Ländereinstellungen vorbelegt werden,

Wenigsten das. Turbo-Pascal hatte nichts davon. :wink:
Mit Lazarus sehe ich grün
Mit Java und C/C++ sehe ich rot

wp_xyz
Beiträge: 4869
Registriert: Fr 8. Apr 2011, 09:01

Re: Dezimaltrenner (DecimalSeparator) in Lazarus falsch

Beitrag von wp_xyz »

Wenn Programme (ich meine nicht Programmiersprachen) den Leuten die Zahlendarstellung anbieten, die sie kennen, gibt es kein Problem.

Euklid
Lazarusforum e. V.
Beiträge: 2808
Registriert: Fr 22. Sep 2006, 10:38
OS, Lazarus, FPC: Lazarus v2.0.10, FPC 3.2.0
Wohnort: Hessen
Kontaktdaten:

Re: Dezimaltrenner (DecimalSeparator) in Lazarus falsch

Beitrag von Euklid »

petwey hat geschrieben:Aber auf die Schnelle kann ich mir durch ein Workaround helfen.


Hallo petwey,

der Workaround ist wahrscheinlich nicht notwendig: Das eigentlich veraltete

Code: Alles auswählen

Decimalseparator:=',';


scheint wunderbar zu klappen. Dazu muss im uses-Bereich die sysutils eingespannt werden.

Viele Grüße, Euklid

Antworten