2013-07-25 9 views
5

まず最初に、私は8086アセンブリに非常に新しく、知識を掴むのはかなり困難でした。それにもかかわらず、私は最善を尽くします。x86で0-9の範囲で乱数を生成する8086アセンブリ

私は0-9の範囲で乱数を生成するコードを記述しようとしています。いくつかの例と提案を調べたところ、これが私の結論です。私は、簡単にするために、検索されたクロック数に何らかの数学的関数を適用していませんでしたまた、私はそれが不要だと思った。私はいくつかの理由で、1,3や9などの数字よりも6,7の倍数のような特定の数字を生成してしまいました。私は、それが値が変わるクロックダニの次数を取っているからです急速に。

私の目的は、後でコードの範囲を1-6に変更するサイコロをシミュレートすることです。 私の質問は、これは私の目的にとって十分であるということですか?またはこれを行うための良い方法がありますか?

コード:@johnfoundによって

RANDGEN:  ; generate a rand no using the system time 
RANDSTART: 
    MOV AH, 00h ; interrupts to get system time   
    INT 1AH  ; CX:DX now hold number of clock ticks since midnight  
       ; lets just take the lower bits of DL for a start.. 
    MOV BH, 57 ; set limit to 57 (ASCII for 9) 
    MOV AH, DL 
    CMP AH, BH ; compare with value in DL,  
    JA RANDSTART ; if more, regenerate. if not, continue... 

    MOV BH, 49 ; set limit to 48 (ASCII FOR 0) 
    MOV AH, DL 
    CMP AH, BH ; compare with value in DL 
    JB RANDSTART ; if less, regenerate. 


    ; if not, this is what we need 
    mov ah, 2h ; call interrupt to display a value in DL 
    int 21h  
RET 

回答、:

私は彼の方法は単純であり、かつ乱数を生成するために、より少ない時間がかかりました。彼は、あなたが単一の乱数を必要とする場合、または乱数の間隔に人間の入力のための休止が含まれる場合にのみ、これが機能すると述べました。もしそうでなければ、数字は全くランダムではありません(私たちが最初に取った種が変化しないので信じています)。私はロールダイスをシミュレートしているので、私の場合は問題ありません。また、コードを再実行する前にユーザーの介入(別のロール)が必要です。

RANDGEN:   ; generate a rand no using the system time 
RANDSTART: 
    MOV AH, 00h ; interrupts to get system time   
    INT 1AH  ; CX:DX now hold number of clock ticks since midnight  

    mov ax, dx 
    xor dx, dx 
    mov cx, 10  
    div cx  ; here dx contains the remainder of the division - from 0 to 9 

    add dl, '0' ; to ascii from '0' to '9' 
    mov ah, 2h ; call interrupt to display a value in DL 
    int 21h  
RET  

は、彼がやったこと: 1.Weはは の2.WeはDXをクリアAXとDXに値を移動しました。 3.私たちは10月12日をCXに移しました。 4. AXをCXで分けたので、DX 5に格納されている0〜9月12日の剰余が得られます。最後に、ASCII '0'(dec 48)をASCIIに '0'〜 '9 '

+0

(あなたが出力(あなたのタイトルが示すように)1〜10の範囲であるか、または0-255たいですあなたの質問は示唆している:* ... 1バイトの乱数を生成する*)?そしてコードは、ASCIIで '0'から' 9'の範囲をしようとしているようです。 – lurker

+0

ええ、タイトルのとおり、正確には0-9です。 – Raf

答えて

6

このトリックは、1つの乱数が必要な場合、または乱数の間隔に人入力のポーズが含まれている場合にのみ機能します。それ以外の場合は、数字はランダムではありません。

多くの乱数が必要な場合は、利用できる擬似乱数アルゴリズムが異なります。あなたはもちろんのすべての乱数生成器は、この方法を使用することができます

mov ax, dx 
    xor dx, dx 
    mov cx, 10  
    div cx  ; here dx contains the remainder of the division - from 0 to 9 

    add dl, '0' ; to ascii from '0' to '9' 

別のノートでは、必要な間隔で番号を取得するために、より簡単な方法があるということです。

+0

私はあなたのコードを試して、それは完璧に動作します。それは私のものと比較して生成する時間がかかりませんでした。しかし、私はいくつかのことを完全には理解していません。 1. xor dx、dx - これは何の目的ですか? 2. dl、 '0'を追加する - DLに '0'を追加して、実際に0-9のASCII値を達成する方法はありますか? – Raf

+0

dlに0を加えていませんが、文字 "0"のASCIIコード= 30h = 48です。このようにして、DLの数字(0〜9)は30h〜39hになります。 「0」から「9」までの文字を含む。何かxor何か= 0常に。 – johnfound

+0

私は何をしましたか:1. DXでの価値をAXに移しました.2。DXをクリアしました。 3.私たちは10月12日をCXに移しました。 DXをCXで分割したので、DX 5に格納されている0〜9月12日の剰余が得られます。最後に、ASCII '0'(dec 48)をASCIIに '0'〜 '9' 。 よろしくお願いいたします – Raf

0

このジョブでは、より小さなオペコードAAM - Ascii Adjust for Multiplicationが見つかりました。このオペコードの作業方法:だから

AH := AL/10 
AL := AL mod 10 

が、それはこのようになります。

mov al, dl 
aam 
add al, '0' 
mov dl, al 
関連する問題