检查最多120的数字是否为素数

时间:2016-03-25 19:40:24

标签: assembly x86 dos

最新问题:(试图检查它是否可以被2整除)

MOV AH, 0 ;reset AH before division
    MOV AL,[myNum] ;move the inputed number to AL
    DIV two ;div 123 / 2;
    CMP AH,0
    JNE inputIsPrime

    ;If 123 % 2 = 0, output 123 / 2.
    DIV ten
    MOV DH,AH

    SUB AL,'0'
    MOV AH,2
    MOV DL, AL
    INT 21h

    MOV divisionCalc,DH

    MOV AH,2
    MOV DL,DH
    INT 21h
    JMP endProg

我正在努力实现这个目标:

  1. 输入数字最多为120.我们称之为“num”。

  2. 如果2,3,5,7,11的数字余数为零,我需要打印除以余数为零的每个数的除法。否则,如果打印num是素数。

  3.   

    e.g。

         

    输入:120。输出:120/2 = 60,120 / 3 = 40。

         

    输入:118,输出:118是素数。

    我做了什么:

    1. 我扫描前3个数字(我不在乎第一个数字是否为零)并且我使用一个简单的算法来构建'num'。我还假设这个数字小于121。

    2. 如果数字可以被(2,3,5,7,11)中的任何一个整除,我会打印msg,否则我会跳过msg打印。

    3. 如果所有带数字的余数为零,我打印出num是素数。

    4. 我不确定我是否完成了这项工作,因为我在运行DOSBox时遇到了一些问题,你能帮我确定一下是否正确吗?

      .MODEL SMALL
      .STACK 100h
      .DATA
      
      DisplayString DB 'Enter number up to 120:', 13,10,'$'
      isPrimeNum DB 'is prime', 13,10,'$'
      ResultStr DB 13,10, '    /    =   ' , 13,10,'$'
      divisionCalc DB ?
      myNum DB ?
      two DB 2
      three DB 3
      five DB 5
      seven DB 7
      ten DB 10
      eleven DB 11
      
          .CODE
      Begin:
          MOV AX,@DATA
          MOV DS,AX
      
          MOV AH,9
          MOV DX,OFFSET DisplayString
          INT 21h
      
          MOV BL,0 ; Initialize BL to zero!
      
          ; //READ 3 DIGITS // ;
          ;read first digit for e.g. '1'
          MOV ah,1h
          INT 21h ;read into AL
          MOV CL,AL
          MOV ResultStr[2], AL
          SUB AL,'0' ; Convert the digit from ASCII to DECIMAL
          MOV myNum,AL
      
          MOV AH,1
          INT 21h
          CMP AL,13 ;is it Enter?
          JE endInput
          MOV ResultStr[3], AL
          SUB AL,'0' ;Not enter, let's save this new char
          MOV CL, AL ; we save the 2nd char to CL
          MOV AL, myNum ; lets move our first char to AL
          MUL Ten ; multiply by 10 the first char
          MOV myNum,AL ;move that to myNum
          ADD myNum,CL ; add to AL the 2nd char.
      
          MOV AH,1
          INT 21h
      
          CMP AL,13 ; is it enter?
          JE endInput
          MOV ResultStr[4], AL
          SUB AL,'0' ;Not enter, let's save this new char
          MOV CL, AL ; we save the 2nd char to CL
          MOV AL, myNum ; lets move our first char to AL
          MUL Ten ; multiply by 10 the first char
          MOV myNum,AL ;move that to myNum
          ADD myNum,CL ; add to AL the 2nd char.
      
          mov AH,1 ; if the number is 3 chars then this will be the enter now. 
          int 21h 
      
          ; // FINISH READING 3 DIGITS // ;
          endInput:
      
                  ; AL = AX / two
              ; AH = AX % two
      MOV AH, 0 ;reset AH before division
      MOV AL,[myNum] ;move the inputed number to AL
      mov CL,[myNum]
      DIV two ;div 123 / 2;
      CMP AH,0
      JNE divThree
      
      ;If 123 % 2 = 0, output 123 / 2.
      
      MOV ResultStr[9], '2'
      
      DIV ten
      MOV DH,AH
      
      ADD AL,'0'
      MOV ResultStr[13], AL
      ADD DH,'0'
      MOV ResultStr[14], DH
      
      MOV AH,9
      MOV DX,OFFSET ResultStr
      INT 21h
      
      divThree:
      MOV AH, 0 ;reset AH before division
      MOV AL,[myNum] ;move the inputed number to AL
      DIV three ;div 123 / 3;
      CMP AH,0
      JNE divFive
      
      ;If 123 % 3 = 0, output 123 / 3.
      MOV ResultStr[9], '3'
      
      DIV ten
      MOV DH,AH
      
      ADD AL,'0'
      MOV ResultStr[13], AL
      ADD DH,'0'
      MOV ResultStr[14], DH
      
      
      MOV AH,9
      MOV DX,OFFSET ResultStr
      INT 21h
      
      divFive:
      MOV AH, 0 ;reset AH before division
      MOV AL,[myNum] ;move the inputed number to AL
      DIV five ;div 123 / 5;
      CMP AH,0
      JNE divSeven
      
      ;If 123 % 5 = 0, output 123 / 5.
      MOV ResultStr[9], '5'
      
      DIV ten
      MOV DH,AH
      
      ADD AL,'0'
      MOV ResultStr[13], AL
      ADD DH,'0'
      MOV ResultStr[14], DH
      
      MOV AH,9
      MOV DX,OFFSET ResultStr
      INT 21h
      
      divSeven:
      MOV AH, 0 ;reset AH before division
      MOV AL,[myNum] ;move the inputed number to AL
      DIV seven ;div 123 / 7;
      CMP AH,0
      JNE divEleven
      
      ;If 123 % 7 = 0, output 123 / 7.
      MOV ResultStr[9], '7'
      
      DIV ten
      MOV DH,AH
      
      ADD AL,'0'
      MOV ResultStr[13], AL
      ADD DH,'0'
      MOV ResultStr[14], DH
      
      MOV AH,9
      MOV DX,OFFSET ResultStr
      INT 21h
      
      divEleven:
      MOV AH, 0 ;reset AH before division
      MOV AL,[myNum] ;move the inputed number to AL
      DIV eleven ;div 123 / 11;
      CMP AH,0
      JE Skip1
      JMP inputIsPrime
      
      Skip1:
      ;If 123 % 11 = 0, output 123 / 11.
      MOV ResultStr[8], '1'
      MOV ResultStr[9], '1'
      
      DIV ten
      MOV DH,AH
      
      ADD AL,'0'
      MOV ResultStr[13], AL
      ADD DH,'0'
      MOV ResultStr[14], DH
      
      MOV AH,9
      MOV DX,OFFSET ResultStr
      INT 21h
      
      JMP endProg
      
      inputIsPrime:
      MOV AH,9
      MOV DX,OFFSET isPrimeNum
      INT 21h
      
      endProg:
      MOV AH,4Ch
      INT 21h
      END Begin
      

1 个答案:

答案 0 :(得分:2)

编程中的一条规则是“不要重复自己”#34;。因此,每次复制代码时,都应该问自己是否可以避免使用它。您可以使用"数组"而不是在单独的代码块中检查每个素数。素数

num     db 118
prims   db 2,3,5,7,11           ; these pimes will be checked

然后在这样的循环中检查它们:

start:  mov cx, 5               ; number of prims to check
        mov si, offset prims

checkPrime:
        xor ah, ah              ; this is faster than mov ah,0
        mov al, [num]
        div byte ptr [si]

        cmp ah,0
        jne skip

        ;...                    ; here you do whatever you want to do with non-primes
                                ; or even jump out of the loop, if all you want is to 
                                ; determine if [num] is a prime

skip:   inc si
        dec cx
        jnz checkPrime

ps:你也可以扫描3位数字"如果你用循环制作它会更好,例如如果你想将它扩展为读取5位数,甚至是可变数量,如1-5位数,则输入16​​位int 我也将"输入数字"分开。部分来自"解码ascii并制作一个int"部分,(首先将所有字符输入缓冲区,然后解码)你可能想重复使用它们;
你也可以使用函数int 21 / A,来获得完整值的缓冲输入