Zurück   Flashforum > Flash > ActionScript > ActionScript 1

Antwort
 
LinkBack Themen-Optionen Ansicht
Alt 12-08-2005, 11:43   #1 (permalink)
FBx
 
Benutzerbild von xlive
 
Registriert seit: May 2003
Beiträge: 968
zahlen vergleichen: 0.42 >= 0.42 = false

hi,

habe eine einfache berechnung, die auch soweit in der test.fla wunderbar funktioniert.
ActionScript:
  1. //test.fla
  2. var zahl1:Number = 0.42;
  3. var zahl2:Number = 20;
  4. var zahl3:Number = 1200;
  5. var zahl4:Number = 25;
  6. var columnB4:Number = new Number(Math.round(((zahl2/zahl3)*zahl4)*100)/100);
  7. trace(columnB4); //Ausgabe: 0.42
  8.  
  9. if (columnB4>=zahl1) {
  10.     trace ("true");
  11. } else {
  12.     trace ("false");
mache ich jetzt das ganze in meiner anwendung, aus der die zahl 1 aus einer .xml kommt, zahl2 und zahl3 aus einer combobox/eingabefeld, wird mir bei der if-abfrage immer false ausgegeben, d.h.
ActionScript:
  1. 0.42 >= 0.42 //false
  2.  
liegt es vielleicht daran, dass die zahl 1 aus der .xml als string ausgelesen wird, und so anders vom interpreter im speicherbereich codiert wird als die Number, somit die 0 und 1 nicht identisch sind, daher = false?
wäre jetzt zumindest meine einzige erklärung.

habe es nun so gelöst.
ActionScript:
  1. var columnB4:Number = new Number((Math.round(((combowert2/1200)*volumen)*100)/100)+0.00001);


gruß xlive
xlive ist offline   Mit Zitat antworten
Alt 12-08-2005, 11:54   #2 (permalink)
Freizeitflasher
 
Benutzerbild von Alphanimal
 
Registriert seit: Jun 2004
Ort: Niederösterreich
Beiträge: 615
du kannst auch den Wert aus der XML (und alle anderen werte) in Numbers konvertieren.
vl hilft das was?
__________________
Some Flash Worx
Alphanimal ist offline   Mit Zitat antworten
Alt 12-08-2005, 13:15   #3 (permalink)
FBx
 
Benutzerbild von xlive
 
Registriert seit: May 2003
Beiträge: 968
schau, dass mach ich doch:
ActionScript:
  1. //ich importiere meine zahl(0.42) und schreibe sie in columnF
  2. var columnF:Number = new Number(xmlpath.childNodes[6].firstChild.nodeValue);
  3.  
  4. //hier schicke ich das ganze durch ein array, um es zu sortieren
  5. personDB.push({min:columnF, max:columnG, .....});
  6. //--
  7. minSortedArr = personDB.slice();
  8. minSortedArr.sortOn("min", Array.NUMERIC);
  9.  
  10. //hier erzuge ich ein number-object
  11. var min:Number = new Number (personDB[i]["min"]);
  12.  
  13. //hier wird der verleichswert berechnet
  14. var columnB4:Number = new Number(Math.round(((combowert2/1200)*volumen)*100)/100);
  15.  
  16. //und da nun beide werte 0.42 sind, müsste eigenlich ein true rauskommen.
  17. if (columnB4>=min){
  18. trace ("true");
  19. }
tut´s aber leider nicht!?
xlive ist offline   Mit Zitat antworten
Alt 12-08-2005, 15:21   #4 (permalink)
Freizeitflasher
 
Benutzerbild von Alphanimal
 
Registriert seit: Jun 2004
Ort: Niederösterreich
Beiträge: 615
extrem krass:
ActionScript:
  1. a = Number("0.42");
  2. b = Number(0.42);
  3. trace(a==b); //false!
  4.  
ausweg:
ActionScript:
  1. trace(a.toString()==b.toString()); //true
  2.  
as sind die kleinen "eigenheiten" von float Werten...
__________________
Some Flash Worx

Geändert von Alphanimal (12-08-2005 um 15:22 Uhr)
Alphanimal ist offline   Mit Zitat antworten
Alt 12-08-2005, 15:38   #5 (permalink)
FBx
 
Benutzerbild von xlive
 
Registriert seit: May 2003
Beiträge: 968
super.danke.
es liegt wirklich daran, dass der interpreter die unterschiedlichen datentypen (strings, number, booleschen werte) in unterschiedlicher reihenfolge der nullen und einsen kodiert. und wenn dann irgendwo an der 15 stelle anstatt einer 0 eine 1 steht, dann ist die ausgabe = false;

ActionScript:
  1. bleibt nur noch die stilfrage;-)
  2. so
  3.  var columnB4:Number = new Number(Math.round(((combowert2/1200)*volumen)*100)/100);
  4. var wertB4:String = columnB4.toString();
  5. if (wertB4>=min && wertB4<=max) {
  6. } 
  7. oder so
  8. ActionScript:
  9. 1
  10. 2
  11.  if (String(columnB4)>=min && String(columnB4)<=max) {
  12. }

gruß xlive
xlive ist offline   Mit Zitat antworten
Alt 12-08-2005, 15:40   #6 (permalink)
................
 
Benutzerbild von Der Frager
 
Registriert seit: Jun 2004
Beiträge: 15.890
Hmmm... Ist ja mal ganz interessant, aber was soll der Mist???
ActionScript:
  1. a = Number("0.42");
  2. b = Number(0.42);
  3. trace(a-b);//5.55111512312578e-17
  4. trace(1-a);//0.58
  5. trace(1-b);//0.58
  6.  
__________________

ternärer Konditionaloperator

+++ Bitte keine Privat-Nachrichten bezüglich Flashfragen! +++
Der Frager ist offline   Mit Zitat antworten
Alt 12-08-2005, 15:58   #7 (permalink)
FBx
 
Benutzerbild von xlive
 
Registriert seit: May 2003
Beiträge: 968
ja das ist mal ne gute frage
stell dir vor du hast eine anwendung, die list einen wert (columnF) aus einer xml. nun berechnest du eine zahl (columnB4). wenn columnB>=columnF ist, dann soll eine ausgabe erscheinen. nehmen wir an, beide werte betragen 0.42. also dann hast du
ActionScript:
  1. 0.42 >= 0.42 //Ausgabe: false.
  2.  
ja, dann sitzt de vor der kiste und machst
um jetzt allen, ja abers vorzubeugen, hier mal das "alte" script.

ActionScript:
  1. stop();
  2. //----------------------------------------------------------------------------------------------
  3. //table content begin
  4. //----------------------------------------------------------------------------------------------
  5. for (var i = 1; i<56; i++) {
  6.     createEmptyMovieClip("container"+i, i);
  7. }
  8. //-------
  9. var xDiv:Number = 0;
  10. var yDiv:Number = 0;
  11. var contentlevel:Number = 10;
  12. var playernum:Number = 0;
  13. var verein:Number = 0;
  14. var vereinheight:Number = 30;
  15. var playerheight:Number = 10;
  16. var playerwidth:Number = 10;
  17. //--
  18. var noresult:Number = 0;
  19. rootnd = mein_xml.childNodes[0].childNodes[5];
  20. var personDB:Array = new Array();
  21. for (var i:Number=droplet1; i<droplet2; i++) {
  22.     for (var k:Number=0; k<rootnd.childNodes[i].childNodes.length; k++) {
  23.         var schleife = rootnd.childNodes[i].childNodes.length;
  24.         var nodes = rootnd.childNodes[i].childNodes[k].childNodes;
  25.         var artikelno = nodes[0].firstChild;
  26.         var pic = nodes[1].firstChild;
  27.         var linkpic = nodes[2].firstChild;
  28.         var xmlpath = rootnd.childNodes[i].childNodes[k];
  29.         var columnF:Number = new Number(xmlpath.childNodes[6].firstChild.nodeValue);
  30.         var columnG:Number = new Number(xmlpath.childNodes[7].firstChild.nodeValue);
  31.         var valuevmin:Number = new Number(Math.round(((columnF*1200)/volumen)*10)/10);
  32.         var valuevmax:Number = new Number(Math.round(((columnG*1200)/volumen)*10)/10);
  33.         //trace(!isNaN(columnF));
  34.         //trace(typeof (columnF));
  35.         //--
  36.         //vmin
  37.         var valuevmin1:String = valuevmin.toString();
  38.         if (valuevmin1.indexOf(".", 0) == -1) {
  39.             valuevmin1 += ".0";
  40.         } else {
  41.             valuevmin1;
  42.         }
  43.         //vmax
  44.         var valuevmax1:String = valuevmax.toString();
  45.         if (valuevmax1.indexOf(".", 0) == -1) {
  46.             valuevmax1 += ".0";
  47.         } else {
  48.             valuevmax1;
  49.         }
  50.         //--
  51.         //personDB.push(columnF);
  52.         personDB.push({min:columnF, max:columnG, vmin:valuevmin1,  vmax:valuevmax1, artikel:artikelno, .....});
  53.     }
  54. }
  55. minSortedArr = personDB.slice();
  56. minSortedArr.sortOn("min", Array.NUMERIC);
  57. //----------------------------------------------------------------------------------
  58. // Sortieren ASC
  59. function sortieren(minSortedArr) {
  60.     var columnB4:Number = ((combowert2/1200)*volumen);
  61.     //-------------------------
  62.     personDB = minSortedArr;
  63.     for (i=0; i<schleife; i++) {
  64.         //-------------------------
  65.         var vminsort:Number = new Number (personDB[i]["min"]);
  66.         var vmaxsort:Number = new Number (personDB[i]["max"]);
  67.         var vmin = personDB[i]["vmin"];
  68.         var vmax = personDB[i]["vmax"];
  69.         var artikel = personDB[i]["artikel"];
  70.         var picture = personDB[i]["picture"];
  71.         var link = personDB[i]["link"];
  72.         var zahlvmin:Number = new Number(vmin);
  73.         var zahlmax:Number = new Number(vmax);
  74.         if (columnB4>vminsort && columnB4<vmaxsort) {
  75.             //trace (artikel + "       " + columnB4 +  " > " + vminsort + " && " + columnB4 + " < " + vmaxsort);
  76.             noresult = 1;
  77.             ausgabe_txt12.text = "";
  78.             //--------------------------------------------------------------
  79.             contentlevel++;
  80.             playernum++;
  81.             if (xDiv == 1) {
  82.                 xDiv = 0;
  83.                 yDiv = content_mc._height;
  84.             }
  85.             // Play_mc attachen und ausrichten
  86.             var ausgabe = content_mc.attachMovie("player_mc", "player_" add playernum, contentlevel);
  87.             ausgabe._x = xDiv*(playerwidth+20);
  88.             ausgabe._y = yDiv+5;
  89.             //------------------------------------------------------------
  90.             ausgabe.vmin = vmin;
  91.             ausgabe.vmax = vmax;
  92.             ausgabe.artikel = artikel;
  93.             ausgabe.link = link;
  94.             ausgabe.picture.loadMovie("./" add picture);
  95.             //-------------------------------------------------------------
  96.             //Balkenanzeige
  97.             ausgabe.balken._x = ((zahlvmin*3)+218);
  98.             ausgabe.balken._width = ((zahlmax-zahlvmin)*3);
  99.             //-------------------------------------------------------------
  100.             //Highlighten
  101.             //Artikel No.
  102.             ausgabe.button.onRollOver = function() {
  103.                 this._parent.button.artikelcolor.textColor = 0xAACEAB;
  104.                 _root["container"+i]._x = 0;
  105.                 _root["container"+i]._y = 325;
  106.                 _root["container"+i].loadMovie(this._parent.link);
  107.             };
  108.             ausgabe.button.onRollOut = function() {
  109.                 this._parent.button.artikelcolor.textColor = 0x0A510A;
  110.                 _root["container"+i].unloadMovie();
  111.             };
  112.             //---------------------------------------------------------------
  113.             //--
  114.             xDiv++;
  115.            
  116.             yDiv = content_mc._height;
  117.             xDiv = 0;
  118.             yDiv++;
  119.             //----------------------------------------------------------------
  120.         }
  121.         //Ende > && < Abfrage
  122.         //Ende schleife
  123.         if (noresult == 0) {
  124.             ausgabe_txt12.text = _root.errorvalue4;
  125.         }
  126.     }
  127.     //result
  128. }
  129. //Ende sortieren()-Funktion
  130. //-------------------------------------------------------------
  131. //Funktion aufrufen:
  132. sortieren(minSortedArr);
  133. //-------------------------------------------------------------
  134. //table content end
  135. //-------------------------------------------------------------
  136.  
xlive ist offline   Mit Zitat antworten
Alt 12-08-2005, 20:04   #8 (permalink)
helpQLODhelp
 
Benutzerbild von bokel
 
Registriert seit: Feb 2002
Ort: Köln
Beiträge: 8.505
Deswegen soll man Gleitkommazahlen auch nie direkt vergleichen, sondern nur den Unterschied zwischen zwei Zahlen messen.

ActionScript:
  1. a = Number("0.42");
  2. b = Number(0.42);
  3. epsilon = 0.0001;
  4. trace(Math.abs(a-b) < epsilon);

Das sollte true ergeben, ist aber ungetestet.
Das Problem ist übrigens nicht flashspezifisch, sondern hat mit der begrenzten Genauigkeit von Gleikommazahlen zu tun.

mfg. r

Geändert von bokel (12-08-2005 um 20:05 Uhr)
bokel ist offline   Mit Zitat antworten
Alt 13-08-2005, 00:55   #9 (permalink)
Techniker
 
Benutzerbild von hgseib
 
Registriert seit: Sep 2003
Ort: 64807
Beiträge: 16.324
"..Das Problem ist übrigens nicht flashspezifisch, sondern hat mit der begrenzten Genauigkeit von Gleikommazahlen zu tun.."
sorry, wenn ich wiederspreche, aber das ist es hier nicht. das dezimalzahlen nicht immer komplett als binäre zahlen wiedergegeben werden können, das ist bekannt. aber der fehler müsste immer der SELBE fehler sein. das ist hier nicht der fall.
zahlen im script werden anders dargestellt (müssen aber intern auch umgerechnet werden, schliesslich ist der script auch nur text), wie die selbe zahl, bei der eine be-/umrechnung gegeben ist.

der 'fehler' liegt offensichtlich darin: das im code angegebene zahlen gerundet werden, was bei berechnungen zur laufzeit nicht der fall ist.
a = 0.42;
trace(0.42-a);
// besonders hierbei könnte man doch einen rundungsfehler erwarten
trace(.42*5944.56733/5944.56733-a);
//
trace(Number("0.42")-a);
trace(parseFloat("0.42")-a);
trace(("0.42").valueOf()-a);
trace((4/10+2/100)-a);
trace((4*Math.pow(10, -1)+2*Math.pow(10, -2))-a);
__________________
die ultimative antwort auf alle programmierfragen: der debugger
mfg h.g.seib www.SeibsProgrammLaden.de
hgseib ist offline   Mit Zitat antworten
Alt 13-08-2005, 19:54   #10 (permalink)
helpQLODhelp
 
Benutzerbild von bokel
 
Registriert seit: Feb 2002
Ort: Köln
Beiträge: 8.505
Das stimmt auch wieder hgseib. Es sieht so aus, als ob der Compiler beim Parsen von Zahlen andere Ergebnisse liefert, als der Flashplayer. Es wäre wirklich schöner, wenn beide gleich arbeiten würden.

mfg. r
bokel ist offline   Mit Zitat antworten
Antwort

Lesezeichen

Themen-Optionen
Ansicht

Forumregeln
Es ist Ihnen nicht erlaubt, neue Themen zu verfassen.
Es ist Ihnen nicht erlaubt, auf Beiträge zu antworten.
Es ist Ihnen nicht erlaubt, Anhänge hochzuladen.
Es ist Ihnen nicht erlaubt, Ihre Beiträge zu bearbeiten.

BB-Code ist an.
Smileys sind an.
[IMG] Code ist an.
HTML-Code ist aus.
Trackbacks sind an
Pingbacks sind an
Refbacks sind an



Alle Zeitangaben in WEZ +1. Es ist jetzt 14:19 Uhr.

Domains, Webhosting & Vserver von Host Europe
Unterstützt das Flashforum!
Adobe User Group


Copyright ©1999 – 2012 Marc Thiele