Entwickler-Ecke
Grafische Benutzeroberflächen (VCL & FireMonkey) - Variable geht über for-Schleife hinaus
maxet - So 20.01.13 17:34
Titel: Variable geht über for-Schleife hinaus
Hallo Leute,
ich habe mit einer ganz simplen for-Schleife ein Problem, das mich verwirrt.
Quelltext:
Delphi-Quelltext
1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17:
| procedure allesnachruecken; var i,j,anzahl_nichtaktiv:integer; begin for i:=0 to 8 do begin anzahl_nichtaktiv:=0; for j:=1 to 30 do begin if not stockwerkwartende[i,j].aktiv then inc(anzahl_nichtaktiv); end; while anzahl_nichtaktiv>0 do begin if not (stockwerkwartende[i,j].aktiv) and (j<30) then stockwerkwartende[i,j]:=stockwerkwartende[i,j+1]; dec(anzahl_nichtaktiv); end; end; end; |
Das Problem habe ich bereits mit einem Haltepunkt und Strg+F7 (Ausdruck auswerten) gefunden: die for-Schleife lässt j über 30 hinaus gehen und beim Zugriff auf den Array stockwerkwartende:
Delphi-Quelltext
1:
| stockwerkwartende:array[0..8,1..30] of leute |
schmiert das Programm natürlich mit einem ERangeError ab.
Bis jetzt habe ich den Fehler nicht gefunden und ich bin ratlos :?!?:
Habt ihr eine Idee?
Vielen Dank im Voraus
maxet
Mathematiker - So 20.01.13 18:07
Hallo,
die Zählschleife wird verlassen, wenn die Zählvariable die Grenze überschreitet. D.h. j wird erhöht und wenn es größer als 30, d.h. also 31, ist, wird die Schleife verlassen.
Zitat: |
Hence the for...to statement is almost, but not quite, equivalent to this while construction:
Delphi-Quelltext 1: 2: 3: 4: 5: 6: 7: 8:
| begin counter := initialValue; while counter <= finalValue do begin statement; counter := Succ(counter); end; end | |
Vorsicht aber! Bei eingeschalteter Optimierung kann j auch nach der Schleife unbestimmt sein.
Zitat: |
After the for statement terminates, the value of counter is undefined. |
Die Zitate sind aus der Delphi-Hilfe.
Aus diesem Grund würde ich die Zählschleife durch eine repeat-until oder while-do-Schleife ersetzen.
Beste Grüße
Mathematiker
jaenicke - So 20.01.13 18:29
Eigentlich sollte auch eine entsprechende Compilerwarnung kommen. :gruebel:
Zitat: |
[DCC Warnung] UnitXXX.pas(xx): W1037 FOR-Schleifenvariable 'j' kann nach Durchlauf undefiniert sein |
Tranx - So 20.01.13 20:38
maxet hat folgendes geschrieben : |
Hallo Leute,
ich habe mit einer ganz simplen for-Schleife ein Problem, das mich verwirrt.
Quelltext:
Delphi-Quelltext 1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17:
| procedure allesnachruecken; var i,j,anzahl_nichtaktiv:integer; begin for i:=0 to 8 do begin anzahl_nichtaktiv:=0; for j:=1 to 30 do begin if not stockwerkwartende[i,j].aktiv then inc(anzahl_nichtaktiv); end; while anzahl_nichtaktiv>0 do begin if not (stockwerkwartende[i,j].aktiv) and (j<30) then stockwerkwartende[i,j]:=stockwerkwartende[i,j+1]; dec(anzahl_nichtaktiv); end; end; end; |
Das Problem habe ich bereits mit einem Haltepunkt und Strg+F7 (Ausdruck auswerten) gefunden: die for-Schleife lässt j über 30 hinaus gehen und beim Zugriff auf den Array stockwerkwartende:
Delphi-Quelltext 1:
| stockwerkwartende:array[0..8,1..30] of leute |
schmiert das Programm natürlich mit einem ERangeError ab.
Bis jetzt habe ich den Fehler nicht gefunden und ich bin ratlos :?!?:
Habt ihr eine Idee?
Vielen Dank im Voraus
maxet |
Nach dem Verlassen ist die Schleifenvariable j nicht definiert. Das meckert eigentlich der Compiler an. Er kann auch 31 sein. Und damit würdest Du in der unterlegten Zeile schon den Grenzwert überschreiten
vieleicht schreibst Du besser:
Delphi-Quelltext
1: 2: 3: 4: 5: 6: 7: 8:
| if (j>=1) and (j<30) then begin while anzahl_nichtaktiv>0 do begin if not (stockwerkwartende[i,j].aktiv) then stockwerkwartende[i,j]:=stockwerkwartende[i,j+1]; dec(anzahl_nichtaktiv); end; end; |
Dann kann die Schleife nie über j/j+1 > 30 gehen!
maxet - Mo 21.01.13 18:21
Danke!
So dumme Fehler übersehe ich also, wenn ich stundenlang vorm Bildschirm hocke ... :autsch:
Aber komisch, der Compiler beachtet das gar nicht!? Naja.
Jetzt funktioniert es wieder :party:
jaenicke - Mo 21.01.13 21:51
maxet hat folgendes geschrieben : |
Aber komisch, der Compiler beachtet das gar nicht!? Naja. |
Wie schon geschrieben, bei mir kommt da die Warnung. ;-)
Entwickler-Ecke.de based on phpBB
Copyright 2002 - 2011 by Tino Teuber, Copyright 2011 - 2025 by Christian Stelzmann Alle Rechte vorbehalten.
Alle Beiträge stammen von dritten Personen und dürfen geltendes Recht nicht verletzen.
Entwickler-Ecke und die zugehörigen Webseiten distanzieren sich ausdrücklich von Fremdinhalten jeglicher Art!