Dividieren in Assembler, immer wieder ein schönes Thema!
Vor allem, wenn eine Kommazahl herauskommt.
Konkret soll in meinem Beispiel 23/7 gerechnet werden. Laut Taschenrechner ~= 3,285714.
Als binäre Näherung habe ich ermittelt: 0000 0011 0100 1001 0010 0100
Das heißt 2^1+2^0+2^(-2)+...+2^(-14) ~= 3.285706
Das Ziel ist also, dass genau diese drei Bytes (Hex $03 $49 $24) hintereinander im Speicher liegen.
Mein Code unten erfüllt diesen Zweck zwar, aber er ist doch recht redundant. Irgendwie finde ich nicht den richtigen Übergang, nachdem das ganzzahlige Ergebnis vorliegt. Ich habe immer das Gefühl, es müsste sich alles mit einer einheitlichen Schleife erledigen lassen.
Was habe ich übersehen? Verbesserungsvorschläge willkommen!
Code
*=$c000
; DIVISION 8-Bit durch 8-Bit
; *mit Nachkommastellen*
ba = $02a7 ; Basisadresse
dvd = ba ; Dividend
dvs = ba+1 ; Divisor
tmp = ba+2 ; Hilfsspeicher
res = ba+3 ; ba+4 ; ba+5 ; Ergebnis
; Beispiel: 23/7 = 3 R 2 ~= 3,285714
; Ergebnis binär (Näherung):
; 2^1
; + 2^0
; + 2^(-2)
; + 2^(-5)
; + 2^(-8)
; + 2^(-11)
; + 2^(-14) ~= 3.285706
;
; Entsprechende Binärzahl:
; 0000 0011 0100 1001 0010 0100
; \ (=$03)/ \ (=$49)/ \ (=$24)/
; \_____/ \_____/ \_____/
; res res+1 res+2
; ($02aa) ($02ab) ($02ac)
; ^ ^ ^
; | \ /
; Ganze Nachkomma-
; Zahl anteil
mydvd = 23
mydvs = 7
lda #<mydvd
sta dvd
lda #mydvs
sta dvs
lda #$00
sta tmp
sta res
sta res+1
sta res+2
ldx #8
loop asl dvd
rol tmp
lda tmp
cmp dvs
bcc skip
sbc dvs
sta tmp
skip rol res+2
rol res+1
rol res
dex
bne loop
lda tmp ; Kein Rest?
beq finish ; dann Ende
ldx #16
loop2 asl tmp
lda tmp
cmp dvs
bcc skip2
sbc dvs
sta tmp
skip2 rol res+2
rol res+1
rol res
dex
bne loop2
finish rts
Alles anzeigen