I'm in the way to implement double dabble algorithm in C to perform binary to BCD notation. I'm using a pic16f876a. I'm not sure, but i guess there's no default operation to do this, so i want to transfer/left shift one bit at a time from the original register to another in this fashion:
0000 0000 0000 11110011 Initialization
0000 0000 0001 11100110 < Left Shift
0000 0000 0011 11001100 <Left Shift
0000 0000 0111 10011000 < Left Shift
add 3 to nibble with 7/111 result ...
I will start by creating 16bits register should i mask the original number's MSB and place it on LSB of the other register? and then lef shift original register?
And eventually get to his final BCD result
BCD (Binary)
100s Tens Ones Original
0010 0100 0011 11110011
I don't know how to drag every individual bit Also i know i'll have to add 3 when nibble is greater than 4, but maybe masking will do the job.I'll be displaying four digits in 7 segment display from 0000 to 3000 i'll be getting from multiplying 16bit resgiter for a constant to get a maximum of 3000 when register is 1111 1111 1111 1111.
thanks in advice
Here is a simple solution. The main()
displays the result in hexadecimal (which must correspond to the initial decimal integer).
NB: you can replace all unsigned
by any unsigned integer type. For instance by uint16_t
for a 16 bits integer (don't forget #include <stdint.h>
)
#include <stdio.h>
unsigned double_dabble(unsigned x) {
unsigned r = 0, mask, d;
int k = 0, nibbles, n, bit;
for(mask = 1 << (sizeof(x) * 8 - 1); mask; mask >>= 1) {
nibbles = (++k + 3) / 4;
for(n = 0; n < nibbles; n++) {
d = r & (0b1111 << (n * 4));
if (d > (4 << (n * 4)))
r += 3 << (n * 4);
}
bit = ((x & mask) != 0);
r = (r << 1) | bit;
}
return r;
}
int main() {
unsigned x = 0b11110011; // 423
printf("x: %d -> BCD: %x\n", x, double_dabble(x));
}
Alternatively here is a simple way to convert an integer to BCD (not using the double dabble algorithm). It uses sprintf+strtod:
unsigned to_BCD(unsigned x) {
char s[20]; // enough even for 64-bits integers !
sprintf(s, "0x%u", x);
return (unsigned) strtod(s, NULL);
}
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.