2.
Tipps und Tricks Teil 4 (Stand: 24.10.2007)
Bedienungsanleitung
und Befehlsliste können beim Programmieren am PC mit Taste F1 aufgerufen
werden.
Zahlenbereich Überschreitung von 32767 beim Rechnen, Begrenzen
Zählen_bis_65535 im word, Zahl 0 bis 65535, Anzeigen mit 1 bis 2 Kommastellen
Zahlen_über_65535 Zähler, Addition, Multiplikation, Division NEU
Phantasie ist wichtiger
als Wissen. (Albert
Einstein)
define Wert1 byte [3] ' Byte 3 Zwischenspeicher 1
define Wert2 byte [4] ' Byte 4 Zwischenspeicher 2
define Wert12 word[2] ' = Byte 3,4 (Überlappung mit Bytes Wert1 und Wert2)
define wert1Bit0 Bit [17] ' für bit-Handling des byte Wert1 (Zwischenspeicher)
define wert1Bit1 Bit [18]
define wert1Bit2 Bit [19]
define wert1Bit3 Bit [20]
define wert1Bit4 Bit [21]
define wert1Bit5 Bit [22]
define wert1Bit6 Bit [23]
define wert1Bit7 Bit [24]
2.4.1) Überschreitung des Zahlenbereichs beim Rechnen
1.
Überschreitung beim
Addieren im Bereich 0 bis 65535
Wert12 =
32000
Wert12 =
wert12 + 20000 ' Ergebnis 52 000
Das Ergebnis ist eine negative Zahl in ccBasic (-19232),
weil das vorderste Bit als Minuszeichen interpretiert wird.
Sie kann aber auch als positive
Zahl bis 65535 interpretiert werden. Zahlenausgabe siehe unten.
2.
Begrenzen bei
Addition und Zählern 0 bis 65535
(anstelle –32768 bis +32767)
(1) Begrenzen beim Rückwärtszählen
bei Null
If
Zaehler > 0 then
Zaehler = Zaehler - 1
Null wird nicht unterschritten (sonst würde 65535 entstehen, -1 in ccBasic)
(2) Begrenzen bei Subtraktion
If Zaehler – wert > 0 then Zaehler = Zaehler – wert else Zaehler = 0
Die Subtraktion wird nicht ausgeführt, wenn es zur Unterschreitung von Null käme.
(3) Begrenzen beim Vorwärtszählen bis +65535
Aufwändiger ist die Begrenzung beim Addieren
Zaehler = Zaehler + 1 ' 65535 darf nicht überschritten werden (65536 wäre 0)
Die Zahlenreihe lautet in ccBasic mit der Interpretation bis 65535 in Klammern:
+32766, +32767, -32768 (+32768), -32767 (+32769), -32765 (+32770),....,-2 (65534), -1 (+65535)
Zur Begrenzung kann man den halben Zählerwert abfragen:
If (Zaehler SHR 1 AND &h7FFF) < 32767 then Zaehler = Zaehler + 1 ' begrenzt auf 65535
If 65535 / 2 < 32767 then ... ist der Beweis in Zahlen, dass die Addition nicht ausgeführt wird.
(4) Begrenzen bei Addition
Bei größeren Werten als +1 muss als Begrenzung von 32766 der halbe Wert abgezogen werden.
Bei variablen Werten gilt:
If (Zaehler SHR 1 AND &h7FFF) < (32766 – wert / 2) then Zaehler = Zaehler + wert ' begrenzt auf 65535 -wert
Die Addition wird nicht ausgeführt, wenn es zu einer Überschreitung käme.
Man kann als Ersatz den maximalen Wert 65535 setzen, indem else angehängt wird.
If ... then .... else Zaehler = -1 ' 65535 ist bei ccBasic die Zahl -1 (Minus Eins)
3.
Dividieren von Zahlen bis 65535
Das Programm
arbeitet im gesamten Zahlenbereich 0 bis 65535.
In diesem
Beispiel wird 52000 durch 10 geteilt. Hierbei wird 10 zerlegt in 2 und 5.
Wert12 =
52000 ' in ccBasic -19232
' Erst wird erst durch 2 geteilt (das
Minus entfernt) und dann durch 5.
wert12 =
wert12 SHR 1 : wert1Bit7 Bit = 0 '
Ergebnis 26000
wert12 = wert12 / 5 ' Ergebnis 5200
(wert12 SHR 1 AND &h7FFF) für Teilen durch 2 und Entfernen von Minus kann auch angewendet werden.
Ist der Nenner eine ungerade Zahl oder könnte als Variable gerade oder ungerade sein, so muss in zwei Stufen gerechnet werden.
In diesem
Beispiel wird 52000 durch 11 geteilt.
Hierbei wird
erst durch 2 geteilt, dann durch 11 und danach wieder mit 2 multipliziert.
Wert12 =
52000 ' in ccBasic -19232
wert12 =
wert12 SHR 1 : wert1Bit7 Bit = 0 '
Ergebnis 26000
wert12 = wert12 / 11 * 2 ' Ergebnis 4726
statt 4727
mit
Rundungsroutine „+ halber Nenner“ (siehe unten) lautet die letzte Zeile
wert12 =
wert12 / 11 + (wert12 + 11) / 11 ' Ergebnis 4727
Diese hier abgewandelte Rundung ist
jedoch nicht 100%ig richtig.
4.
Überschreitung beim
Multiplizieren (Zerlegung eines Faktors)
Wird
das Ergebnis beim Multiplizieren größer 32767 , muss ein Faktor zerlegt werden.
Das Verfahren kann im Zahlenbereich 0 bis 65535 benutzt werden.
Beispiel:
1002 * 43 = 43086 soll auf LCD ausgegeben werden.
Zerlegung: 43 / 10 = 4 und 43 MOD 10 = 3
Multiplikation: 1002*4 und 1002*3 (= 4008 und 3006)
Ergebnis:
4 Stellen sind 4008 + 3006/10 = 4308
Einer ist 3006 MOD 10 = 6
5.
Überschreitung beim
Multiplizieren (Nenner dividieren)
Nutzungsgrad = 100* Eindauer /
GesamtZeit ' als Prozentzahl
Wenn (100* Eindauer) die Zahl 32767
überschreitet, entsteht ein unsinniges Ergebnis.
Dies ist bei Eindauer = 328 Minuten bereits der Fall.
Lösung :
Nutzungsgrad = Eindauer /
(GesamtZeit / 100) ' als Prozentzahl
Die
Prozentzahl kann auch gebildet werden, indem der Nenner (Klammer beachten) durch 100 geteilt wird.
Dieses Verfahren ist besonders
zweckmäßig, wenn die Zeit in Minuten oder Sekunden gemessen wird.
6.
Überschreitung beim
Multiplizieren (variabler Faktor)
Nutzungsgrad
= 100* Eindauer / GesamtZeit ' als Prozentzahl
Wenn (100*
Eindauer) die Zahl 32767 überschreitet, entsteht ein unsinniges Ergebnis.
Dies ist bei Eindauer = 328 Minuten bereits der Fall.
Lösung :
If Eindauer > 327 then wert3 = 10 else wert3 = 1
Nutzungsgrad = 100 / wert3 * Eindauer /
(GesamtZeit / wert3)
Wert3 ist ein Zwischenspeicher (define wert3 byte), der auch für andere Rechnungen benutzt wird.
Ab Eindauer 328 wird der Wert 100 durch 10 dividiert. Die Multiplikation ergibt nun nur 3280.
Als Ausgleich wird im Nenner auch durch 10 dividiert (Klammer beachten).
Sinngemäß ist bei der Nachkommastelle zu verfahren (siehe oben Bewertung des Modulowertes):
Rest = 100 / wert3 * Eindauer MOD (GesamtZeit / wert3) ' Rest ohne
Bewertung
Für Komma
1-stellig gilt, falls (GesamtZeit / wert3) *10 nicht 32767 überschreitet:
wert2 = 100 / wert3 * Eindauer MOD (GesamtZeit / wert3) *10 / (GesamtZeit / wert3)
7.
Überschreitung beim
Multiplizieren (Byte-Zerlegung)
Beispiel: 3000 * 15 = 45000 überschreitet 32767 und soll in ein word gespeichert werden.
Die Zahl 3000 wird aufgeteilt in High- und Low-Byte (Linkes und rechtes Byte)
Linkes Byte 3000 / 256 = 11 rechtes Byte 3000 MOD 256 = 184
Nun wird mit beiden Bytewerten multipliziert. 11 * 15 und 184 * 15
Linkes Byte beträgt 11*15 + 184*15 / 256 ' Ergebnis 175
Rechtes Byte beträgt 184*15 MOD 256 ' Ergebnis 200
Bei der Ausgabe als word wird die Zahl über 32767 als eine negative Zahl gezeigt.
Die folgende Zahlenausgabe würde das Ergebnis zeigen 45000 (= 175 * 256 + 200)
2.4.2) Zahlenausgabe ohne Vorzeichen 0 bis 65535 (statt
–32768 bis 32767)
Beispiel:
Ein Zähler (word) kann auch über 32767 hinaus zählen. Die Zahl wird nun von der
c-control negativ interpretiert.
Man kann aber weiter zählen bis
65535. Wie kann man nun die Zahl anzeigen?
Define
Zaehlerwert word
Die Zahl wird durch 10 geteilt, indem mit dem Befehl „Schiebe Rechts 1 Bit“ durch 2 geteilt, das Minus durch Maskierung entfernt und dann durch 5 geteilt wird.
Die Teilung der Zahl beim Einer hat den Vorteil, dass keine führende Null ausgegeben werden muss.
Außerdem hat man eventuell direkt die Einer als Kommastelle.
Zahl4 = (
Zaehlerwert SHR 1 AND &h7FFF) / 5 ' 4 Stellen
Einer = (( Zaehlerwert + 32768)
MOD 10 + 18) MOD 10 ' 1 Stelle (evt. Kommastelle)
Braucht man 2 Kommastellen, dann muss bei deren Ausgabe beachtet werden, dass eine führende Null für 0 bis 9 notwendig ist.
Zahl3 = (
Zaehlerwert SHR 1 AND &h7FFF) /
50 '
3 Stellen
Zahl2 = (( Zaehlerwert + 32768)
MOD 100 + 168) MOD 100 ' 2 Stellen
Zum Testen kann man anstelle Zaehlerwert den Timer 0 bis 65535 anzeigen lassen.
2.4.3) Überschreiten des Zahlenbereichs beim Zählen (größer
65535)
Noch größere
Zahlen kann man durch Übertrag auf
einen zweiten Zähler erhalten z.B. 999 999 oder 2 559 999.
Define
ZaehlerA word
Define ZaehlerB byte
Beispiel: if Ereignis then goto
Zaehlen else goto Ende
#Zaehlen
if
ZaehlerA = 9999 then goto Uebertrag ' nur bis 4 Stellen zählen
ZaehlerA = ZaehlerA + 1 : Goto Ende ' 4
Stellen
#Uebertrag
ZaehlerB =
ZaehlerB + 1 : ZaehlerA = 0 ' 5. und 6.
Stelle (möglich bis 255)
#Ende ' Ergebnis ZaehlerB enthält die 5. und 6. Stelle (0 bis
99) und ZaehlerA enthält 4 Stellen.
Die Zahlen sind bereits dezimal sortiert.
Deshalb kann die große Zahl auf LCD oder mit Terminalprogramm leicht ausgegeben werden, indem nach ZaehlerB sofort ZaehlerA folgen kann.
Noch größere Zahlen siehe nächster Abschnitt „Addieren“.
Natürlich kann der Übergang auch bei 32767 erfolgen, doch sind dann Rechnen und Zahlen-Ausgabe schwierig.
ZaehlerA =
ZaehlerA + 1 ' ZaehlerA bis 32767
If ZaehlerA >= 0 then goto Ende ' (wenn
Zaehler negativ wird)
ZaehlerB =
ZaehlerB + 1 : ZaehlerA = 0 ' (erfolgt der
Übertrag auf ZaehlerB)
#Ende '
2.4.4) Überschreiten des
Zahlenbereichs beim Addieren (größer 65535)
Beim Beispiel wird statt einer
Variablen ein fester Wert (371) addiert.
Beispiel: if Ereignis then goto
Addieren else goto Ende
#Addieren
ZaehlerA = ZaehlerA + 371 ' erst addieren
if
ZaehlerA < 1000 then goto Ende ' 3 Stellen überschritten ?
ZaehlerB =
ZaehlerB + ZaehlerA / 1000 ' Übertrag von ZählerA
ZaehlerA =
ZaehlerA MOD 1000 ' 3 Stellen
#Ende
ZaehlerB enthält Tausender und ZaehlerA enthält 3 Stellen (Hunderter, Zehner und Einer).
Die maximale Zahl beträgt 255 999, wenn ZaehlerB als byte definiert wurde. Bei ZaehlerB als word kann die Zahl 32 767 999 werden.
Nutzt man zusätzlich die Ausgabe ohne Vorzeichen beträgt die maximale Zahl 65 535 999.
ZählerA darf natürlich auch 4 Stellen ( /10000) enthalten. Dann sind die Grenzen 2 559 999 bzw. 655 359 999.
2.4.5) Dividieren von Zahlen (größer 65535)
Die Zahl 386 780 liegt in diesem Beispiel wieder in ZaehlerB ( 0 bis 255) und ZaehlerA (0 bis 9999).
ZaehlerB =
38 '
Wert *10000 = 380000
ZaehlerA =
6780 ' 4
Stellen max 9999
Diese Zahl 386780 soll durch 3 geteilt werden. Das Ergebnis muss also 128926 sein.
ZaehlerA = ZaehlerA / 3 + 10000 / 3 * ZaehlerB MOD 3 ' = 6780 / 3 + 10000/3*2 = 8926
ZaehlerB =
38 / 3 '
= 12 Rest 2
2.4.6) Überschreiten des
Zahlenbereichs beim Multiplizieren (größer 65535)
Das Prinzip der Zerlegung eines
Faktors siehe obige Beispiele Multiplikation bis 65535.
Beispiel: 6315 * 93 = 587 295
Die Zahl darf im word nur 32767
betragen. Deshalb wird die Zahl 6315 zerlegt beispielsweise in 63 Rest 15.
WertB = 6315
/ 100 * 93 + 6315 MOD 100 * 93 / 100 ' Hunderter mit Übertrag von Rest
63 * 93 + 15 * 93 /100 = 5859 + 13 = 5872
WertA = 6315
MOD 100 * 93 MOD 100 ' Rest 2 Stellen
15* 93 MOD 100 = 95
Das maximale Ergebnis der Multiplikation darf 3 276 700 betragen mit beliebigen Faktoren.
Bei noch größeren Zahlen müssen beide Faktoren (hier x und y) zerlegt werden in Hunderter und Rest.
x * y =
(Hx + Rx) * (Hy + Ry)
Für Anwender bereits fertig ausmultipliziert:
= Hx * Hy + Rx * Hy + Hx * Ry + Rx * Ry
Hunderter mit Summe aller
Überträge der Reste
WertB = ((x / 100 * y / 100) /100 + (x MOD 100 * y / 100) /100
+ (x /100 * y MOD 100) /100 + (x
MOD 100 * y MOD 100) /100
Zunächst Summe aller Reste,
dann Rest 2 Stellen
WertA = ((x / 100 * y / 100) MOD 100 + (x MOD 100 * y / 100) MOD 100 +
+ (x /100 * y MOD 100) MOD 100 + (x MOD 100 * y MOD 100) MOD
100 ) MOD
100
--------------------
ENDE Tipps und Tricks Teil 4
------------ nach_oben
-----------------
zurück zu Tipps Teil 1 Tipps_und_Tricks_Teil_2 Startseite