16位masm汇编实现筛法,状压求十万以内素数

.model small
.data
    table byte 3,12500 dup (0);;0和1不是质数
    i word 0
    j word 0

.stack 4096

.code
main proc far
start:
    mov ax,@data
    mov ds,ax
    mov di,offset table
    mov i,2
    mov cx,350
    s0:
        mov ax,i
        mov dx,0                                        ;dx:ax/bx=ax...dx
        
        mov bx,8
        div bx
        push cx
            mov cx,dx                                   ;余数 位移
            mov si,ax                                   ;商   偏移地址
            mov dx,1
            shl dl,cl                                   ;移位
            mov bx,di
            test [bx][si],dl                                ;noprime[i]
            jnz s0continue                                  ;不是质数
        pop cx

        push cx
        mov ax,i
        mov j,ax                                            ;j=i;i*j<=10w;j++
        s1:
            mov ax,j
            mul i
            and dx,dx
            jz setbit                               ;dx非零,若乘积大于等于65536,要跳过去特判,大于10w要跳出s1

            ;dx>=1
            cmp dx,1                                ;等于1、大于1
            ja s0continue                           ;dx大于1要continue s0.等于要特判ax是否满足
            cmp ax,1000011010100000B
            ja s0continue                           ;ax大于阈值,continue s0

            setbit:
                mov bx,8
                div bx
                mov cx,dx
                mov si,ax
                mov bx,di
                mov dl,1
                shl dl,cl
                or [bx][si],dl
            inc j
        jmp s1
        s0continue:
        inc i
        pop cx
    loop s0
    
    mov cx,65533
    mov i,2
    output:
        mov dx,0
        mov ax,i
        mov bx,8
        div bx

        mov si,ax
        mov bx,di

        push cx
            mov cl,dl
            mov dl,1
            shl dl,cl
            test [bx][si],dl
            jnz outputconti
            mov dx,0
            mov ax,i
            call print16b_dec
        outputconti:
        pop cx
        inc i
    loop output

    mov cx,34464
    mov i,0
    output2:
        mov dx,1
        mov ax,i
        mov bx,8
        div bx

        mov si,ax
        mov bx,di

        push cx
            mov cl,dl
            mov dl,1
            shl dl,cl
            test [bx][si],dl
            jnz output2conti
            mov dx,1
            mov ax,i
            call print16b_dec
        output2conti:
        pop cx
        inc i
    loop output2
    
    mov ax,4c00h
    int 21h
main endp

print16b_dec proc near;用%d输出16bit,参数放在dx:ax,dx有0和1两种情况
    mov bx,10000D   ;dx:ax/bx=ax...dx
    div bx
    mov bx,dx       ;余数
    call print1dec
    mov ax,bx
    mov dx,0
    mov bx,1000D
    div bx
    mov bx,dx
    call print1dec
    mov ax,bx
    mov dx,0
    mov bx,100D
    div bx
    mov bx,dx
    call print1dec
    mov ax,bx
    mov dx,0
    mov bx,10D
    div bx
    mov bx,dx
    call print1dec
    mov ax,bx
    call print1dec
    mov dl,0dh
    mov ah,2h
    int 21h
    mov dl,0ah
    mov ah,2h
    int 21h
    ret
print16b_dec endp

printbig_dec proc near;用%d输出一个16bit数加上65536,参数放在ax

    mov dx,1
    mov bx,10000D   ;dx:ax/bx=ax...dx
    div bx
    mov bx,dx       ;余数
    call print1dec
    mov ax,bx
    mov dx,0
    mov bx,1000D
    div bx
    mov bx,dx
    call print1dec
    mov ax,bx
    mov dx,0
    mov bx,100D
    div bx
    mov bx,dx
    call print1dec
    mov ax,bx
    mov dx,0
    mov bx,10D
    div bx
    mov bx,dx
    call print1dec
    mov ax,bx
    call print1dec
    mov dl,0dh
    mov ah,2h
    int 21h
    mov dl,0ah
    mov ah,2h
    int 21h

printbig_dec endp

print1dec proc near;用来%d输出一个10进制位,参数放在ax
    mov dx,ax
    add dl,30h
    mov ah,2h
    int 21h
    ret
print1dec endp

end start

运行环境masm6.11
复杂度大概是\(O(n\log n)\)

posted @ 2019-11-21 22:09  wawcac  阅读(...)  评论(...编辑  收藏