Das deutsche QBasic- und FreeBASIC-Forum Foren-Übersicht Das deutsche QBasic- und FreeBASIC-Forum
Für euch erreichbar unter qb-forum.de, fb-forum.de und freebasic-forum.de!
 
FAQFAQ   SuchenSuchen   MitgliederlisteMitgliederliste   BenutzergruppenBenutzergruppen  RegistrierenRegistrieren
ProfilProfil   Einloggen, um private Nachrichten zu lesenEinloggen, um private Nachrichten zu lesen   LoginLogin
Zur Begleitseite des Forums / Chat / Impressum
Aktueller Forenpartner:

Bug in FORMAT?

 
Neues Thema eröffnen   Neue Antwort erstellen    Das deutsche QBasic- und FreeBASIC-Forum Foren-Übersicht -> Allgemeine Fragen zu FreeBASIC.
Vorheriges Thema anzeigen :: Nächstes Thema anzeigen  
Autor Nachricht
steini



Anmeldungsdatum: 17.09.2004
Beiträge: 58

BeitragVerfasst am: 21.03.2012, 12:32    Titel: Bug in FORMAT? Antworten mit Zitat

Also entweder nutze ich FORMAT falsch oder beim Runden gibt es einen Bug:

Code:
#INCLUDE "vbcompat.bi"
DIM value AS DOUBLE
value=0.009
PRINT FORMAT(value, "0.00") '0,01 erwartet aber 0,00 ausgegeben!
value=0.019
PRINT FORMAT(value, "0.00")
SLEEP
END


Auf 0,02 rundet er korrekt, auf 0,01 jedoch nicht. Hier wird die dritte Nachkommastelle offensichtlich komplett ignoriert. Sollte das etwa Absicht sein?
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
MOD
Fleißiger Referenzredakteur


Anmeldungsdatum: 10.09.2007
Beiträge: 1003

BeitragVerfasst am: 21.03.2012, 19:28    Titel: Antworten mit Zitat

Es kann durchaus ein Bug sein. FORMAT und auch PRINT USING sind recht komplex und wir haben desöfteren während der Arbeit an der Referenz "Unstimmigkeiten" entdeckt. Ein weiteres Problem scheint zu sein, dass nicht genau ersichtlich ist, wie sich die Befehle eigentlich verhalten sollten. erst kürzlich wurde das auch im englischen Forum angesprochen.

In naher Zukunft wird sich daran wohl leider nichts ändern, die Befehle müssen grundlegend überdacht und neugeschrieben werden. Ich werde es bei Gelegenheit aber dennoch weitergeben.
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
ThePuppetMaster



Anmeldungsdatum: 18.02.2007
Beiträge: 1839
Wohnort: [JN58JR]

BeitragVerfasst am: 21.03.2012, 19:52    Titel: Antworten mit Zitat

geschockt ... seit wann "rundet" der "FORMAT" befehl?!?!?

Ich glaube, das liegt eher am Double. Nutze mal Single. da sollte es gehen.


MfG
TPM
_________________
[ WebFBC ][ OPS ][ ToOFlo ][ Wiemann.TV ]
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
ytwinky



Anmeldungsdatum: 28.05.2005
Beiträge: 2624
Wohnort: Machteburch

BeitragVerfasst am: 21.03.2012, 20:48    Titel: Antworten mit Zitat

@tpm: ich zitiere mal aus der Referenz:
Zitat:
'numerischer_Ausdruck' ist ein beliebiger Ausdruck, der als DOUBLE gehandhabt wird.

@Steini: kuckma, ob dir das hilft. Ansonsten hättest du noch die Möglichkeit die Werte eben VOR der Benutzung von Format() zu runden..
Die Benutzung von Format ist(wie MOD schon gesagt hat) nicht ganz einfach zwinkern
Ich hoffe, daß ich da bald mal Klarheit reinbringen kann^^
@MOD: still working on it..
Gruß
ytwinky
_________________
v1ctor hat Folgendes geschrieben:
Yeah, i like INPUT$(n) as much as PRINT USING..
..also ungefähr so, wie ich GOTO..
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden E-Mail senden Website dieses Benutzers besuchen
Muttonhead



Anmeldungsdatum: 26.08.2008
Beiträge: 565
Wohnort: Jüterbog

BeitragVerfasst am: 21.03.2012, 20:58    Titel: Antworten mit Zitat

für eine Rundungsroutine hab ich mich mal hier bedient:

http://www.dreael.ch/Deutsch/BASIC-Knowhow-Ecke/Gleitkommazahlen.html

funzt auf 2 stellen hinterm Komma...

Code:
function Float2String(value as double) as string
  'Versuch einer kleinen Rundungsroutine
  'in Anlehnung an dreaels "Variante 3: Rückdivisionsfreie Rundung"

  function="0"
  dim as integer l
  dim as string vstring,newstring
  vstring = str(int(100! * abs(value) + .5)) 'value wird erweitert,gerundet und zum "INTEGERSTRING"(öhhm... jahh) XD
  l=len(vstring)'entsprechend der Länge des Strings wird das Komma(Punkt) nach 3 zu unterscheidenen Fällen gesetzt
  if l=1 then newstring ="0.0" & vstring                           '1.Fall
  if l=2 then newstring ="0." & vstring                            '2.Fall
  if l>2 then newstring =left(vstring,l-2) & "." & right(vstring,2)'3.Fall
  if sgn(value)=-1 then newstring ="-" & newstring                           'zum Schluss eventuell ermitteltes negatives Vorzeichen einfügen
  function=newstring
end function


print float2string(0.009)
print float2string(0.019)
sleep


Mutton
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden E-Mail senden
MisterD



Anmeldungsdatum: 10.09.2004
Beiträge: 3071
Wohnort: bei Darmstadt

BeitragVerfasst am: 22.03.2012, 02:23    Titel: Antworten mit Zitat

ThePuppetMaster hat Folgendes geschrieben:
geschockt ... seit wann "rundet" der "FORMAT" befehl?!?!?

Ich glaube, das liegt eher am Double. Nutze mal Single. da sollte es gehen.


MfG
TPM


http://www.freebasic.net/wiki/wikka.php?wakka=KeyPgFormat sagt:

0 - Digit placeholder: If the number has fewer digits than there are zeros (on either side of the decimal) in the format expression, leading or trailing zeros are displayed. If there are more digits to the right of the decimal than zeros in the format, the number is rounded. If there are more digits to the left of the decimal than zeros in the format the digits are all displayed
_________________
"It is practically impossible to teach good programming to students that have had a prior exposure to BASIC: as potential programmers they are mentally mutilated beyond hope of regeneration."
Edsger W. Dijkstra
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
steini



Anmeldungsdatum: 17.09.2004
Beiträge: 58

BeitragVerfasst am: 25.03.2012, 12:05    Titel: Antworten mit Zitat

Ok, ich danke euch für eure Statements.

Nachdem nun klargestellt ist, dass FORMAT bedauerlicherweise in mehreren Fällen nicht ordnungsgemäß rundet und damit für meine Rechnungssoftware unbrauchbar da einfach zu unzuverlässig ist, habe ich folgende FORMAT2-Funktion geschrieben, vielleicht hat ja einer Verwendung.

Man kann sie zum Runden von Währungen oder Maßen exakt wie FORMAT verwenden, mit der Einschränkung, dass grundsätzlich genau eine Vorkomma-Null ausgegeben wird und der Format-String f einen Punkt enthalten muss. In Programmen, in denen Währungen oder Maße auf mindestens eine Nachkommastelle gerundet werden, könnt ihr so die bereits vorhandenen FORMAT einfach durch FORMAT2 ersetzen und euch richtiger Ergebnisse erfreuen zwinkern

Code:
#INCLUDE "vbcompat.bi"
DECLARE FUNCTION FORMAT2(wert AS DOUBLE, f AS STRING) AS STRING

PRINT FORMAT(0,"#.00")+"    "+ FORMAT2(0,"#.00")
PRINT FORMAT(.099,"0.000")+"    "+ FORMAT2(.099,"0.000")
PRINT FORMAT(.009,"0.00")+"    "+ FORMAT2(.009,"0.00")+" <- FORMAT rundet hier falsch!"
PRINT FORMAT(.019,"0.00")+"    "+ FORMAT2(.019,"0.00")
PRINT FORMAT(.099,"0.##")+"    "+ FORMAT2(.099,"0.##")
PRINT FORMAT(.099,"0.00")+"    "+ FORMAT2(.099,"0.00")
PRINT FORMAT(-13,"0.00")+"    "+ FORMAT2(-13,"0.00")
PRINT FORMAT(-.099,"0.000")+"    "+ FORMAT2(-.099,"0.000")
PRINT FORMAT(-.009,"0.00")+"    "+ FORMAT2(-.009,"0.00")+" <- FORMAT rundet hier falsch!"
PRINT FORMAT(-.019,"0.00")+"    "+ FORMAT2(-.019,"0.00")
PRINT FORMAT(-.099,"0.##")+"    "+ FORMAT2(-.099,"0.##")
PRINT FORMAT(-.099,"0.00")+"    "+ FORMAT2(-.099,"0.00")
SLEEP
END

FUNCTION FORMAT2(wert AS DOUBLE, f AS STRING) AS STRING
DIM a AS DOUBLE  = .0000001#
DIM w AS DOUBLE
DIM AS INTEGER nachkomma, nachkomma2
DIM r AS STRING
IF wert < 0 THEN a = -a
nachkomma = LEN(f) - INSTR(f,".")
w = 10^nachkomma
IF wert = 0 THEN r = " 0" ELSE r = STR((CINT(wert*w)/w)+ a)
IF INSTR(r,".") = 0 THEN r = r + "."
nachkomma2 = LEN(r)-INSTR(r,".")
IF nachkomma2 > nachkomma THEN
 r = LEFT$(r,LEN(r)-(nachkomma2 - nachkomma))
 IF RIGHT$(f,1) <> "0" THEN
  WHILE RIGHT$(r,1) = "0": r = LEFT$(r,LEN(r)-1): WEND
 ENDIF
ELSE
 IF RIGHT$(f,1) = "0" THEN r = r + STRING$(nachkomma-nachkomma2,"0")   
END IF
MID$(r,INSTR(r,"."),1) = ","
FORMAT2 = LTRIM$(r)
END FUNCTION
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
Jojo
alter Rang


Anmeldungsdatum: 12.02.2005
Beiträge: 9736
Wohnort: Neben der Festplatte

BeitragVerfasst am: 25.03.2012, 14:14    Titel: Antworten mit Zitat

steini hat Folgendes geschrieben:

Nachdem nun klargestellt ist, dass FORMAT bedauerlicherweise in mehreren Fällen nicht ordnungsgemäß rundet und damit für meine Rechnungssoftware unbrauchbar


Geldbeträge niemals mit Fließkommazahlen darstellen! Kopf schütteln Du schießt nicht mit FORMAT, sondern mit der Verwendung von SINGLE und DOUBLE selbst ins Bein. Da es in FB keinen Festkomma-Datentyp gibt, solltest du Geldbeträge grundsätzlich als Integer abspeichert und mit der gewünschten Granularität multiplizieren, also z.B. mit 100 wenn du zwei Nachkommastellen benötigst. Bei der Ausgabe kannst du dann entweder direkt nach SINGLE / DOUBLE konvertieren und durch 100 teilen, oder noch besser, den Wert vor dem Komma mit Betrag \ 100 und den Bruchteil mit Betrag Mod 100 darstellen.
_________________
» Die Mathematik wurde geschaffen, um Probleme zu lösen, die es nicht gäbe, wenn die Mathematik nicht erschaffen worden wäre.
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden Website dieses Benutzers besuchen
steini



Anmeldungsdatum: 17.09.2004
Beiträge: 58

BeitragVerfasst am: 25.03.2012, 17:15    Titel: Antworten mit Zitat

Dass man Geldbeträge idealerweise als Integer speichert ist mir bewusst, ich kann das in meinem umfangreichen Programm nur leider nicht mehr ändern.
Es ändert aber nichts an der Tatsache, dass FORMAT nicht korrekt funktioniert und darum ging es hier in dem thread.
Nach oben
Benutzer-Profile anzeigen Private Nachricht senden
Beiträge der letzten Zeit anzeigen:   
Neues Thema eröffnen   Neue Antwort erstellen    Das deutsche QBasic- und FreeBASIC-Forum Foren-Übersicht -> Allgemeine Fragen zu FreeBASIC. Alle Zeiten sind GMT + 1 Stunde
Seite 1 von 1

 
Gehe zu:  
Du kannst keine Beiträge in dieses Forum schreiben.
Du kannst auf Beiträge in diesem Forum nicht antworten.
Du kannst deine Beiträge in diesem Forum nicht bearbeiten.
Du kannst deine Beiträge in diesem Forum nicht löschen.
Du kannst an Umfragen in diesem Forum nicht mitmachen.

 Impressum :: Datenschutz