So I've been going through the "learn asm in 28 days" and stopped for a while, but I'm back on it, and I just don't understand this part about LUT. Im trying to find the sine of 30, please tell me what's wrong:


Code:
LD     A, 30
   LD     H, 0
    LD     L, A
    LD     DE, sine_table
    ADD    HL, DE
    LD     A, (HL)
    LD     H, 0
    LD     L, A
   b_call(_DispHL)
    RET


All it says is "66." I don't know how to make it display decimal/fractions, but there's probably something else wrong.
The _DispHL bcall displays the contents of the hl register as if it was an unsigned 16-bit integer, holding values 0 through 65535. What is the structure of your LUT? Based on your code, it would need at least 90 words (180 bytes); every two bytes would be the sine of an angle. It would look something like:


Code:
Sine_table:
.dw 0   ;sine of 0 degrees is 0
.dw 1143 ;sine of 1 degree is 0.01745
.dw 2287 ;sine of 2 degrees is 0.034899
...


Where did I pull those numbers from? The sine of an angle can be any value from -1 to 1. It is negative from angle=-180 to 0 degrees, and positive from 0 to 180 degrees. All you need in your LUT table are the sines from 0 to 180, and to give them maximum precision, I multiplied each sine by 65535. Therefore, 65535 corresponds to 1, and 0 to 0, allowing you to effectively store decimal numbers.

What about the sine of 90-180 and -180 to 0? For 90 to 180, you simply take the sine of 180-angle. Sine of 160, for instance, is the same as sine of 180-160 = 20, which you have in your table. For -180 to 0, just take the negative sine of the negative angle. For the sine of -80, find the sine of 80 degrees and negate it.

Since you have two bytes for each of your angles, you'll have to change your code to add de to hl twice, then get both h and l from the table. Alternatively, you could have only a single byte for each angle in the table, as you seem to have from your sample there, but you'll get much less precision on each number.
Well I understand how you can get full range of sin values from its symmetry, but I still don't really understand how you display the decimal answer between -1 and 1. The sine table is this:


Code:

sine_table:
    ; The lookup table
.DW    $0000, $0004, $0009, $000D, $0012, $0016, $001B, $001F, $0024
.DW    $0028, $002C, $0031, $0035, $003A, $003E, $0042, $0047, $004B
.DW    $004F, $0053, $0058, $005C, $0060, $0064, $0068, $006C, $0070
.DW    $0074, $0078, $007C, $0080, $0084, $0088, $008B, $008F, $0093
.DW    $0096, $009A, $009E, $00A1, $00A5, $00A8, $00AB, $00AF, $00B2
.DW    $00B5, $00B8, $00BB, $00BE, $00C1, $00C4, $00C7, $00CA, $00CC
.DW    $00CF, $00D2, $00D4, $00D7, $00D9, $00DB, $00DE, $00E0, $00E2
.DW    $00E4, $00E6, $00E8, $00EA, $00EC, $00ED, $00EF, $00F1, $00F2
.DW    $00F3, $00F5, $00F6, $00F7, $00F8, $00F9, $00FA, $00FB, $00FC
.DW    $00FD, $00FE, $00FE, $00FF, $00FF, $00FF, $0100, $0100, $0100


And from my understanding, if I wanted the sine of 30, I would find the 30th address after the location of label "sine_table" But if HL points to that address, cant you just put (HL) into a register, then get it to display HL? That won't be a decimal though....[/code]
Is that the sine table and code provided by ASM in 28 Days? If so, its code is wrong, as those are what are called 8.8 fixed-point numbers: 8 bits before the decimal point, and 8 bits after. Here's some pseudo-code for what you want to do:
Code:
    ld a,30
    ld d,0
    ld e,a
    ld hl,sine_table
    add hl,de
    add hl,de
    ld a,(hl)     ;v
    inc hl         ;v
    ld h,(hl)     ;v
    ld l,a          ;this is like ld hl,(hl), but there's no such opcode

    ;now display it [pseudocode]
    display h as an 8-bit integer
    display a decimal point
    display l*(1000/256) as an integer
    ret
Oooooh, the guide isn't wrong, it mentioned the 8.8 fixed point, but it didn't say what it was. That makes so much more sense now. Sorry, but one last question. For the sine_table you did, it was in base-10 right? how did you go from .dw 1143, to its actual value of 0.01745?

it seems more accurate too
Ratchetx7 wrote:
Oooooh, the guide isn't wrong, it mentioned the 8.8 fixed point, but it didn't say what it was.
It is wrong. It increments one byte per degree, while it needs to increment two bytes per degree.[/quote]
Quote:
That makes so much more sense now. Sorry, but one last question. For the sine_table you did, it was in base-10 right? how did you go from .dw 1143, to its actual value of 0.01745?

it seems more accurate too
No sorry necessary! When you're manipulating these values inside your program, you leave them as integers, because your calculator's CPU has no floating-point instructions. You need special routines to manipulate 8.8 numbers, though, including addition, subtraction, multiplication, and division.
Also, a little note if you're going to stick to numbers 0-90, you can use "a" to multiply by 2. It's not any smaller but it is a slight bit faster Wink

I'd like to help with your other questions, but my math is awful and i don't even remember what to do with sine anymore (other than make a fancy sin(X) graph).
chickendude wrote:
Also, a little note if you're going to stick to numbers 0-90, you can use "a" to multiply by 2. It's not any smaller but it is a slight bit faster Wink

I'd like to help with your other questions, but my math is awful and i don't even remember what to do with sine anymore (other than make a fancy sin(X) graph).
My most recent use of it in a z80 program was figuring out the x-component and y-component of the velocity for shots fired at a specific angle in Obliterate.
Is source included? I feel like it's something i should know as it seems to have a lot of uses. I made a little demo a while ago that had to use some physics-y equations (to calculate how much velocity was needed to hit the ball so that its highest point reached the line):
http://www.mirari.fr/fDNI
Someone was asking about whether it'd be too processor intensive to draw the path the ball would take or something, i forget now Razz

EDIT: Errr... doesn't like that image, changed into a link.
  
Register to Join the Conversation
Have your own thoughts to add to this or any other topic? Want to ask a question, offer a suggestion, share your own programs and projects, upload a file to the file archives, get help with calculator and computer programming, or simply chat with like-minded coders and tech and calculator enthusiasts via the site-wide AJAX SAX widget? Registration for a free Cemetech account only takes a minute.

» Go to Registration page
Page 1 of 1
» All times are UTC - 5 Hours
 
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum

 

Advertisement