Em 15/2/2010 13:23, sergio masci escreveu: > > On Sun, 14 Feb 2010, Josh Koffman wrote: > > = >> On Tue, Feb 9, 2010 at 12:36 AM, Josh Koffman wrot= e: >> = >>> Hi all. I'm thinking of a project where I'll have a 9 bit binary >>> number, and I'll want to display it on a 3 digit 7 segment display. To >>> do this I'll need to extract the hundreds, tens, and ones digits from >>> the number. The PICList.org website has an 8 bit version to do this >>> (http://www.piclist.org/techref/microchip/math/radix/b2oth-8b3d-jsv.htm= ). >>> Has anyone seen a 9 bit version (or a higher bit version that's easily >>> foolable, I guess up to 16 bit would be easy)? >>> = >> I've decided to limit myself to an input of 255 for now. Once I get >> that working I'll move on to getting the extra bit to work and adding >> on to my existing 8 bit to H,T,O. >> >> I'm starting to work with the routine linked to in my original email. >> I'm rewriting it in my own style to make sure I understand how it >> works. I got the hundreds conversion (at least I think I understand >> it). I must admit I've lost the scent on the tens and ones. The author >> notes that they should be run together, but I can't see why. In fact >> it seems to me that if they are run together then the routine won't >> output the number of tens anywhere. Also shouldn't the hundreds >> routine feed into the tens routine? >> >> Man I'm confused. Continuing web searching, but any help would be apprec= iated. >> = > lets say you want to convery the binary number 359 to ascii digits. Dont = > worry that it's shown as decimal or greater than 255 for now. > > So what you would normally do is look at the 100s column and take the 3 = > then the 10s column and take the 5 then the 1s column and take the 9. Ok = > so how do we take a digit from a column on a computer. Well what we = > actually do is take '1' away from that column until we get to '0' and we = > count how many times we are able to do this. If we write this in pseudo = > code we get: > > For the 100s column > > value =3D 359 > count =3D 0 > > while value >=3D 100 do > value =3D value - 100 > count =3D count + 1 > done > > at this point we end up with > > value =3D 59 > count =3D 3 > > It's important that we start with the highest column first. > > For the 10s column > > count =3D 0 > > while value >=3D 10 do > value =3D value - 10 > count =3D count + 1 > done > > now we end up with > > value =3D 9 > count =3D 5 > > Now at this point you can easily see that the '1' column is whats left in = > 'value' > > Now to clear up the confusing bits. > > decimal 359 is binary 01 0110 0111 > decimal 100 is binary 00 0110 0100 > decimal 10 is binary 00 0000 1010 > decimal 1 is binary 00 0000 0001 > > decimal 300 is binary 01 0010 1100 > decimal 50 is binary 00 0011 0010 > > When we take the 3 from the 100s (hundreds) column we are trying to = > convert > binary 0100101100 to binary 0000000011. > > When we take the 5 from the 10s (tens) column we are trying to convert = > binary 0000110010 to binary 0000000101. > > so the easiest way to do this is to repeatedly take binary 0100101100 fro= m = > binary 0101100111 (359) and count in units (binary 0000000001). > > 0101100111 (359) - 0001100100 (100) =3D 0100000011 (259) ; count =3D 1 > 0100000011 (259) - 0001100100 (100) =3D 0010011111 (159) ; count =3D 2 > 0010011111 (159) - 0001100100 (100) =3D 0000111011 (59) ; count =3D 3 > > so at this point we have converted 'value' from 0101100111 (359) to = > 0000111011 (59) and 'count' to 0000000011 (3) > > doing the same for the 10s (tens) we get: > > 0000111011 (59) - 0000001010 (10) =3D 0000110001 (49) ; count =3D 1 > 0000110001 (49) - 0000001010 (10) =3D 0000100111 (39) ; count =3D 2 > 0000100111 (39) - 0000001010 (10) =3D 0000011101 (29) ; count =3D 3 > 0000011101 (29) - 0000001010 (10) =3D 0000010011 (19) ; count =3D 4 > 0000010011 (19) - 0000001010 (10) =3D 0000001001 (9) ; count =3D 5 > > so at this point we have converted 'value' from 0000111011 (59) to > 0000001001 (9) and 'count' to 0000000101 (5) > > now if we look at the pseudo code again - just the 100s (hundreds) for = > now: > > value =3D 359 > count =3D 0 > > while value >=3D 100 do > value =3D value - 100 > count =3D count + 1 > done > > > we see a horrible '>=3D' which kind of complicates things if we are tryin= g = > to convert this pseudo code into assembly language. We can rearrange = > things to make them easier like this: > > value =3D 359 > count =3D 0 > > while (value - 100) > 0 do > value =3D value - 100 > count =3D count + 1 > done > > Another way to think about "X > 0" is "is X not negative". If you have = > enough bits in your variables and you are using 2's complement = > arithmetic (which tends to be available on most processors these days) = > then this is a very easy test to make. > > e.g. > > 0000111011 (59) - 0001100100 (100) =3D 1111010111 (-41) > > simply by looking at the most significant bit (the left most bit) and = > testing if it is a '0' or a '1' we can see if the result is positive = > or zero (for bit =3D 0) or negative (for bit =3D 1). > > So we can actually convert the pseudo code to > > value =3D 359 > count =3D 0 > > while ((value - 100) & 512) =3D=3D 0 do > value =3D value - 100 > count =3D count + 1 > done > > If we tried to do this on a variable that had only 8 bits we would be = > restricting ourselves to numbers on the range -128 to +127 (because we = > want to use the most significant bit for the sign. If we use 16 bits then = > we increase our range to -32768 to +32767. > > The above pseudo code would then become > > value =3D 359 > count =3D 0 > > while ((value - 100) & 32768) =3D=3D 0 do > value =3D value - 100 > count =3D count + 1 > done > > Which is really really easy to convert to PIC assembly code! > > It is well worth using multiprecision arithmetic on a PIC (going from 8 = > bit variables to 16 bit variable) to simplify maths. > > Also a very important aspect of multiprecision arithmetic on an 8 bit CPU = > like the PIC is the ability to calculate addresses greater than 255!!! > > > I hope this helps. > > Regards > Sergio Masci > = There is an interesting implementation which is used by MPLAB-C18 library (file itobcd.asm). It is a very efficient serialized method, it uses only shifts and adds. It is worthy a try. Best regards, Isaac __________________________________________________ Fa=E7a liga=E7=F5es para outros computadores com o novo Yahoo! Messenger = http://br.beta.messenger.yahoo.com/ = -- = http://www.piclist.com PIC/SX FAQ & list archive View/change your membership options at http://mailman.mit.edu/mailman/listinfo/piclist