base:mathematics_in_assembly_part_7
no way to compare when less than two revisions
Differences
This shows you the differences between two versions of the page.
— | base:mathematics_in_assembly_part_7 [2015-04-17 04:32] (current) – created - external edit 127.0.0.1 | ||
---|---|---|---|
Line 1: | Line 1: | ||
+ | ====== Prologue ====== | ||
+ | |||
+ | Now that I managed to send Cactus my contribution to his magazine' | ||
+ | |||
+ | ====== Mathematics in Assembly - 7 ====== | ||
+ | |||
+ | Finally, we are discussing approaches to divide numbers. But let's start slowly on that as well, with dividing by constant numbers. | ||
+ | |||
+ | So we want to divide by a constant number. Those who read the previous chapters thoroughly will quickly get the idea of just generating tables for that matter. Simple tables which can be read using the divisor as index. This, of course, is possible but what to do if a constant amount of values has to add up to a specific integer value? I'll just mention an example to illustrate the problem. | ||
+ | |||
+ | Let's say, we want to divide an arbitrary number by a constant value, for example 5, and then receive exactly 5 resulting values that add up to the original number. All that of course as fast as possible. You may not know where one would have to solve such a problem. I needed it just one time until now, namely in the zoom scroller of the Plush demo " | ||
+ | |||
+ | ====== Memory Efficient ====== | ||
+ | |||
+ | The simplest approach would be to read the quotient from tables. Those would be, for example, a table containing the truncated result numbers and another one containing the decimals of those result numbers. This result value rounded, we already have the first value. The quotient is added to the unrounded value (i.e. doubled) and we have the second value. We then add this quotient until we have all our rounded values needed. This approach is accurate but, despite the tables used, quite slow, as there are four 16 bit additions and four roundings performed for this example. How to do it faster? | ||
+ | |||
+ | ====== Fast ====== | ||
+ | |||
+ | For this example, one could just generate 5 separate tables for the values, one for each of them. But there shall be no memory wasted unnecessarily, | ||
+ | |||
+ | ====== Fast and Memory Efficient ====== | ||
+ | |||
+ | I'll just skip the mathematical explanation for this and tell it without any further redue - one single table is generated, which looks just like this for the mentioned example: | ||
+ | |||
+ | < | ||
+ | 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, [...] | ||
+ | </ | ||
+ | |||
+ | As one can see, each of the rising table values is present 5 times in a row. Now this table, which obviously is simple enough to quickly generate it instead of pre-calculating it, has to be read out correctly. In this example it's done like this: | ||
+ | |||
+ | < | ||
+ | lda table+$00,x | ||
+ | sta value1 | ||
+ | lda table+$02,x | ||
+ | sta value2 | ||
+ | lda table+$04,x | ||
+ | sta value3 | ||
+ | lda table+$03,x | ||
+ | sta value4 | ||
+ | lda table+$01,x | ||
+ | sta value5 | ||
+ | </ | ||
+ | |||
+ | The x register contains the value to be divided by 5. Simple as that. Please note how to define the different table offsets: the middle (value 3) has got the biggest offset (constant-1), | ||
+ | |||
+ | I learned this approach when I looked at HCL's zoom scroller in " | ||
+ | |||
+ | Regards, | ||
+ | |||
+ | KRILL/PLUSH | ||
base/mathematics_in_assembly_part_7.txt · Last modified: 2015-04-17 04:32 by 127.0.0.1