Amorphka készítette az első 191 byte-os verziót. Egy kicsit átpofoztam és lement 100 byte-ra. 99-et szerettem volna, de az már nem ment. Sajnos a 100 byte-os verzió (v7.0) a bitek temetőjébe került, így ez a 101 byte-os verzió (v6.0, 2001-01-16).
A konvergencia kritérium |z|^2-re nem 4 lett, hanem 2*PI. Ezzel is lehetett pár byte-ot spórolni.
Használata kicsit nehézkes, mert 3 argumentumot kell beírni (delta, Re(z0), Im(z0); jobb-felső sarok koordinátái kellenek). A hely spórolás miatt 32 bites IEEE szabványos lebegőpontos formátumban szóközök nélkül. A beírásban a DOS-ban sokat használt alt+(num keypad) megoldás segít. Nem lehet a konvertált 12 karakterben NULL (0), Backspace (8), LF (10), CR (13) karakter, mert azt a command.com értelmezné.
Én a három számot és perl-lel konvertáltam IEEE formátumba, azaz háromszor $float=pack("f", $arg);
és az eredményt unpack("C4", $float);
segítségével lehet leellenőrzini, hogy nem tartalmaz-e tiltott karaktert. A három $float-ot kell összefűzni. Ha van benne whitespace karakter, akkor még a macskaköröm is kell bele. Ha van benne macskaköröm, akkor azt escape-elni kell (azt hiszem. Rég volt.).
És végül a várva várt kód. Szerintem olvasmányos :-)
DOSSEG
.486
_code SEGMENT BYTE PUBLIC USE16 "TEXT"
ASSUME CS:_code, DS:_code, SS:_code
ORG 100h
Main:
;RGB-Palette-------------------------------------------------------
mov al,13h ;VGA 320x200x256 on
int 10h
xor ax, ax ; init VGA mode before Setting color table
; It seems by default first color is 0 after going to VGA mode
mov dx, 03c9h
SetColorTable:
; only lower 6 bits are used to generate color table
LIMIT:
out dx,al ;Send R
out dx,al ;Send G
out dx,al ;Send B
inc ax ; ugly but saves 1 byte
jnz SetColorTable
;--FPUInit-------------------------------------------------------------------
GO:
mov bl, 83h ; PSP
mov ax, 0a000h ; VIDEO RAM
mov es, ax
fldpi ; PI
fadd st(0), st(0) ; 2PI
fld qword ptr [bx+16] ; ci, 2PI
LoopRow:
fld qword ptr [bx+8] ; cr, ci, 2PI
mov si, 320 ;320 Colum
LoopPixel:
mov cl,63 ; convergation loop
fld st(0) ; znr, cr, ci, 2PI
fld st(2) ; zni, znr, cr, ci, 2PI
LoopConverg:
fld st(0) ; zni, zni, znr, cr, ci, 2PI
fmul st(0), st(0) ; zni^2, zni, znr, cr, ci, 2PI
fld st(2) ; znr, zni^2, zni, znr, cr, ci, 2PI
fmul st(2), st(0) ; znr, zni^2, zni*znr, znr, cr, ci, 2PI
fmulp st(3), st(0) ; zni^2, zni*znr, znr^2, cr, ci, 2PI
fld st(0) ; zni^2, zni^2, zni*znr, znr^2, cr, ci, 2PI
fadd st(0), st(3) ; |zn|^2, zni^2, zni*znr, znr^2, cr, ci, 2PI
fcomp st(6) ; |zn|^2 > 2PI
; zni^2, zni*znr, znr^2, cr, ci, 2PI
fstsw ax ; store flag for the future
fsub st(0), st(3) ; zn_i^2-c_r, zni*znr, znr^2, cr, ci, 2PI
fsubp st(2), st(0) ; zni*znr, z(n+1)r, cr, ci, 2PI
fadd st(0), st(0) ; 2*znr*zni, z(n+1)r, cr, ci, 2PI
fadd st(0), st(3) ; z(n+1)i, z(n+1)r, cr, ci, 2PI
and ah, bl ; test the result of comp bl cotains 83h
loopnz LoopConverg
fcompp ; drop top 2 elemets [cr, ci, 2PI]
mov al, cl
stosb
fadd qword ptr [bx] ; c_r += D_r [cr+Dr, ci, 2PI]
dec si
jnz LoopPixel
fcomp st(0) ; drop top element [ci, 2PI]
fsub qword ptr [bx] ; c_i -= D_i [ci-Dr, 2PI]
dec dl ; was init in initialising dx for out :-)
jnz LoopRow
;------ END ------------------------------------
mov ah, 1 ;Wait KeyPressed
int 21h
mov ax, 3 ;Turn off Graphics Screen (80x25)
int 10h
int 20h
_code ENDS
END Main
Hát nem szép? :-)
Lehet keresni benne a felesleges byte-okat! Egy biztosan van benne, csak nem tudom, hogy hol. Ha van tipp, kérem kommentezzétek meg!
PS.: Emlékszem, hogy ebből a projektből nőtte kis magát a "Hogyan küldjünk bináris file-t bat file-ban" projekt. Az is szép volt. :-)
+jegyzések