MIPS 中的算法问题

发布于 2024-09-10 21:32:43 字数 2104 浏览 1 评论 0原文

我正在重写 MIPS 汇编中的 Project Euler 问题的答案,但我无法让这个答案输出正确的答案。我在过去的一个小时里检查了代码,我无法弄清楚我的方法有什么问题(因为当答案比这个高出 200,00+ 时我得到了 33165),所以我发现了问题一定是我的语法不稳定。我在这里做的事情是不是很愚蠢,比如使用保留寄存器?

## p1.asm
## 
## Andrew Levenson, 2010
## Project Euler, Problem 1
## In MIPS Assembly for SPIM

## Calculate the sum, s, 
## of all natural numbers, n,
## Such that n < 1000.
        .text
        .globl  main

main:
        ori     $8, $0, 0x0     # Init sum s in $8 to 0
        ori     $9, $0, 0x0     # Init variable number n in $9 to 0
        ori     $10, $0, 0x3    
        ori     $11, $0, 0x5
        la      $14, lim         


loop:
retry:
        addiu   $9, $9, 0x1     # Increment n by 1

    # Is n less than 1000?
        sltiu   $15, $9, 1000   # if n >= 1000 then jump to print
        beq     $15, $0, print  # if $15 == 0 

        sll     $0, $0, $0      # no op


    # Is n a multiple of three or five?
        div     $9, $10         # n / 3
        mflo    $12             # $12 = floor( n / 3 ) 
        mfhi    $13             # $13 = n mod 3 

        bne     $13, $0, retry  # if n mod 3 != 0 then retry
        sll     $0, $0, $0      # no op
        beq     $13, $0, sum    # else, print
        sll     $0, $0, $0      # no op

        div     $9, $11         # n / 5
        mflo    $12             # $12 = floor( n / 5 ) 
        mfhi    $13             # $13 = n mod 5 

        bne     $13, $0, retry  # if n mod 5 != 0 then retry
        sll     $0, $0, $0      # no op

    # If we've made it this far, n is good!
sum:
        addu    $8, $8, $9      # s = s + n

        j       loop            # jump to loop
        sll     $0, $0, $0      # no op


print:
        li      $v0, 1          # system call #1 - print int
        move    $a0, $8
        syscall                 # execute

exit:   
        li      $v0, 0xA        # system call #10 - exit
        syscall 



## End of Program

## Variable declarations    
                .data
lim:            .word   1000    # loop bound

编辑:代码自发布以来已进行调整。进行了建议的修复,但仍然产生大约 100,000 的答案。 :(

I'm rewriting my answer(s) to Project Euler questions in MIPS assembly, and I can't get this one to output the correct answer. I've gone over the code for the past hour, and I can't figure out what's wrong with my approach (as I am getting 33165 when the answer is a cool 200,00+ higher than that), so I figure the problem must be my shakiness with the syntax. Is there something foolish I am doing here, like using a reserved register?

## p1.asm
## 
## Andrew Levenson, 2010
## Project Euler, Problem 1
## In MIPS Assembly for SPIM

## Calculate the sum, s, 
## of all natural numbers, n,
## Such that n < 1000.
        .text
        .globl  main

main:
        ori     $8, $0, 0x0     # Init sum s in $8 to 0
        ori     $9, $0, 0x0     # Init variable number n in $9 to 0
        ori     $10, $0, 0x3    
        ori     $11, $0, 0x5
        la      $14, lim         


loop:
retry:
        addiu   $9, $9, 0x1     # Increment n by 1

    # Is n less than 1000?
        sltiu   $15, $9, 1000   # if n >= 1000 then jump to print
        beq     $15, $0, print  # if $15 == 0 

        sll     $0, $0, $0      # no op


    # Is n a multiple of three or five?
        div     $9, $10         # n / 3
        mflo    $12             # $12 = floor( n / 3 ) 
        mfhi    $13             # $13 = n mod 3 

        bne     $13, $0, retry  # if n mod 3 != 0 then retry
        sll     $0, $0, $0      # no op
        beq     $13, $0, sum    # else, print
        sll     $0, $0, $0      # no op

        div     $9, $11         # n / 5
        mflo    $12             # $12 = floor( n / 5 ) 
        mfhi    $13             # $13 = n mod 5 

        bne     $13, $0, retry  # if n mod 5 != 0 then retry
        sll     $0, $0, $0      # no op

    # If we've made it this far, n is good!
sum:
        addu    $8, $8, $9      # s = s + n

        j       loop            # jump to loop
        sll     $0, $0, $0      # no op


print:
        li      $v0, 1          # system call #1 - print int
        move    $a0, $8
        syscall                 # execute

exit:   
        li      $v0, 0xA        # system call #10 - exit
        syscall 



## End of Program

## Variable declarations    
                .data
lim:            .word   1000    # loop bound

EDIT: Code adjusted since being posted. Made fixes suggested, but it still yields an answer off by approximately 100,000. :(

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

恏ㄋ傷疤忘ㄋ疼 2024-09-17 21:32:43

通过在每个循环中将 $9 增加 3 ,您会丢失许多 5 的倍数,从 5 开始...

更新:通过分支时$9 不能被 3 整除,然后不能被 5 整除,您只能保留 3 5 的倍数。

更新:您必须删除以下行:

bne     $13, $0, retry  # if n mod 3 != 0 then retry

By incrementing $9 by 3 at each loop, you're missing many multiples of 5, starting with 5...

UPDATE: by branching when $9 is not divisible by 3, and then by 5, you're only keeping the multiples of 3 and 5.

UPDATE: You must remove the following line:

bne     $13, $0, retry  # if n mod 3 != 0 then retry
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文