In QTSPIM Many applications in mathematics involve computing various values of t
ID: 3689434 • Letter: I
Question
In QTSPIM
Many applications in mathematics involve computing various values of the sin function. It can be proven that
sin(x) = x – x 3 /3! + x5 /5! - x 7 /7! + …
for all radian values of x. It is important to remember that x must be expressed in radians, not degrees ( radians = 180 degrees). Of course, this is an infinite sum, so we can’t hope to actually add all of these values up! The good news is that the later terms get so small that a partial sum can provide a very nice approximation for the value of sin(x).
You are to write a double precision function (result returned in $f0) called sin with one double precision parameter (in $f12), along with a little driver program for testing your function. Your function should use the summation formula as an approximation for the value of sin(x), using the following guide for terminating the summation:
If the absolute value of the next term is less than 1.0e-15, then terminate the summation (and don’t even bother to add in that next term).
Even though the summation is valid for all values of x, there is a problem with convergence when you use values of x having absolute values greater than 30 or so. You may assume that we will test your program with values within this range.
Here is a sample execution of my code:
Let's test our sin function!
Enter a (radian) value for x (or 999 to exit): 0
Our approximation for sin(0) is 0
Enter a (radian) value for x (or 999 to exit): 1
Our approximation for sin(1) is 0.8414709848078965
Enter a (radian) value for x (or 999 to exit): 10
Our approximation for sin(10) is -0.54402111088906224
Enter a (radian) value for x (or 999 to exit): -10
Our approximation for sin(-10) is 0.54402111088906224
Enter a (radian) value for x (or 999 to exit): 1.570796326794896 [/2]
Our approximation for sin(1.5707963267948959) is 1
Enter a (radian) value for x (or 999 to exit): -.5232
Our approximation for sin(-0.5232) is -0.49965461045512305
Enter a (radian) value for x (or 999 to exit): -.5235987755982988 [-/6]
Our approximation for sin(-0.52359877559829882) is -0.5
Enter a (radian) value for x (or 999 to exit): 999
Come back soon!
Explanation / Answer
sin:
addi $sp, $sp, -4 # adjust stack for $ra
sw $ra, 0($sp) # save the return address to stack
addi $s1, $zero, 1 # set $s1 (counter to 1)
add $s2, $zero, $zero
mov.d $f6, $f12
mov.d $f10, $f12
loopsin:
mov.d $f4, $f12 # (re)set $f4 = $f0 = x
addi $s0, $zero, 1 # (re)set $s0 to 2
addi $s1, $s1, 2 # add 2 to counter
for1: slt $t0, $s0, $s1 #loop x^y
beq $t0, $zero, exit1
mul.d $f4, $f4, $f12 # $f4 = $f4 x $f4
addi $s0, $s0, 1
j for1
exit1:
move $s0, $s1 # set counter to high value
addi $t1, $zero, 1 # set $t1 to 1
l.d $f2, const1
for2: slt $t0, $s0, $t1
bne $t0, $zero, exit2
mtc1.d $s0, $f8
cvt.d.w $f8, $f8
mul.d $f2, $f2, $f8
addi $s0, $s0 -1
j for2
exit2:
div.d $f4, $f4, $f2 # $f4 = (x^y) / y!
abs.d $f8, $f4
l.d $f16, test # exit if $f4 < 1.0e-15
c.lt.d $f8, $f16
bc1t exitsin
bne $s2, $zero, goadd # if $s2 != 0 goadd
sub.d $f6, $f6, $f4 # x = x - ((x^y) / y!)
addi $s2, $s2, 1 # add 1 to $s2 add next round
j loopsin
goadd:
add.d $f6, $f6, $f4 # x = x + ((x^y) / y!)
add $s2, $zero, $zero # reset $s2 to 0 sub next round
j loopsin
exitsin:
mov.d $f0, $f6
lw $ra, 0($sp) # restore the return address
addi $sp, $sp, 4 # adjust stack pointer to pop item
jr $ra # return
main: la $a0, intro # output intro
li $v0, 4
syscall
loop: la $a0, req # output request radian
li $v0, 4
syscall
li $v0, 7 # input value
syscall
l.d $f16, flag # exit if 999 was entered
c.eq.d $f16, $f0
bc1t out
la $a0, ans1 # output text part(1) of answer
li $v0, 4
syscall
mov.d $f12, $f0 # move input into $f12 print and to pass to sin
li $v0, 3
syscall
la $a0, ans2 # output text part(2) of answer
li $v0, 4
syscall
jal sin # call function sin
mov.d $f12, $f0 # move return $f0 into $f12 to print
li $v0, 3
syscall
j loop
out: la $a0, bye # display closing
li $v0, 4
syscall
li $v0, 10 # exit from the program
syscall
.data
intro: .asciiz "Let's test our sin function! "
req: .asciiz " Enter a (radian) value for x (or 999 to exit): "
ans1: .asciiz "Our approximation for sin("
ans2: .asciiz ") is "
line: .asciiz " "
bye: .asciiz "Come back soon!"
const1: .double 1.0
test: .double 0.000000000000001
flag: .double 999.0
Related Questions
drjack9650@gmail.com
Navigate
Integrity-first tutoring: explanations and feedback only — we do not complete graded work. Learn more.