i have array of size 100
uint8_t a[100] = {1,1,1,1,0,0,0,0, .......}
first off, should i even be using uint8_t for this ? or is there a better data type for this particular need ? im only using it to avoid memory problems.
treating those 1s and 0s as bits, how can i get a hex value ? for instance
hex = f0....
i can probably come up with a really long way(using a ton of if/switch statements) to achieve this, however im wondering if there is a simpler way to do it.
even a simple example pointing me in the right direction would be appreciated.
Using 800 bits to store 100 bits worth of information may well be silly.
Using bytes to represent your data is probably sensible on an eight bit architecture, but pack the bits.
first off, should i even be using uint8_t for this ?
Well no you should not be being so wasteful in the first place. You are taking up 8 bytes to encode just one byte, so you should be gathering the data into bytes in the first place.
If you have what you said and want to compress them then push the bits one at a time into a byte something like this ( not tested just off the top of my head )
int index = 0
uint8_t acc = 0;
while (index < 96) {
acc = 0;
for (int i=0; i<8; i++){
acc = acc << 1;
if(a[index + i) == 1 ) acc |= 1;
}
// at this point acc will have a value in it consisting of 8 bits
Serial.println(acc,HEX); // or what ever you want to do with it.
index = index + 8;
}
I would do that as
byte a[100] = {0xf0, 0xf1, 0xf2,}; // etc. 0x indicates hex. Or 0b11110000, 0b11110001, B11110011, B11110100 etc. for binary, with B or 0b to show binary
How did you get that data in the first place ?
Are they constant data ?
You can use 'byte' instead 'uint_8'. They are the same.
You could write a binary number like this: byte x = B00001111;
I'm confused about your question.
I guess you want to convert them into binary numbers.
Suppose you received a number of '1's and '0's and put them into an array. Suppose you want to convert them into 8 bit binary numbers (to able to print them as hexadecimal numbers).
You could use a loop and the bit manipulation macros.
If you receive bits, you could put them directly into 8-bit binary numbers.
Is the first bit in the array the MostSignificantBit (bit 7) ?
ok it seems that my question was rather ambigious. sorry for that ill explain in more detail. perhaps you guys might be able to suggest something better.
i have a certain array of data, that i needed converted into a bit stream so i could analyze it.
based on certain condition the bit i get is 1 or 0
to illustrate it goes something like this.
uint8_t a[100];
int data[200] = {100,200,100,200,200,200,......} //this is data that i receive as another part of the program.
//this is the part i did to get a bit stream.
for (int i = 0, j=0; i<200;i++,j++){
if (data[i] == 100 && data[i+1] == 200)
a[j] = 1;
else if (data[i] == 200 && data [i+1] == 200)
a[j] = 0;
else
Serial.println("Error");
}
i could alternately use a Serial.print("1"); or Serial.print("0"); to analyze the bit stream if there is some way to store the values into a hex number directly.
i do hope i have explained things better.
i think i should give mikes code a try and see if i can get it to do what i want.
To start, if you only need to store 1's and 0's, I would use a boolean data type.
bool a[100] = {0,1,0,1...};
If you know how large your number needs to be, you can do something like this:
unsigned long a = 0;
uint8_t data[200] = {100,200,100,200,200,200,......} //this is data that i receive as another part of the program.
//this is the part i did to get a bit stream.
for(int i = 0; i < 200; i++){
if(data[i+1] == 200){
if(data[i] == 100) a |= (1<<i);
}
else{
Serial.println("Error");
}
}
Serial.println(a, HEX);
To start, if you only need to store 1's and 0's, I would use a boolean data type.
...which still waste seven bits
Does nothing in this world make sense!?!?!
Actually, it probably makes sense when you understand the implementation.
Good to know. Thanks, AWOL.
Logically, "bool as bit" makes sense and the instruction set supports that, but C doesn't like data types it can't take the address of, so, bits are out
well mikes code helped me out. thanks a lot mike.
i will try and see how i can use that to directly store values as hex there by not wasting space.
thanks for the code chad, ill see if that works for me.
learned some things about bit manipulation. this is great.!
thank you all .
I was wondering to myself if using bitWrite()
into an array would work for packing the bits. I wasn't able to figure out how to do it without a nested if loop. Maybe with a clever function to translate a bit location in a full array down to the array element index and bit location within the element. (This looks like a job for modulo man! XD)
Here is what I was playing with (including my failed attempt commented out) for the insanely curious:
byte dataStore[13];
boolean dataBit = false;
void setup()
{
Serial.begin(115200);
delay(1000); // arbitrary delay to allow time for ERW's auto-Serial-Monitor to open the virtual COM port.
// put your setup code here, to run once:
/* // This didn't work. Can't seem to figure out how to get bitWrite to set a bit past a valid lvalue for the target. Probably can't.
for (char i = 0; i < (sizeof(dataStore) * 8); i++)
{
bitWrite(*dataStore, i, dataBit);
dataBit = !dataBit;
}
*/
for (char i = 0; i < (sizeof(dataStore) / sizeof(dataStore[0])); i++)
{
for (char j = 0; j < (sizeof(dataStore[0]) * 8); j++)
{
bitWrite(dataStore[i], j, dataBit);
dataBit = !dataBit;
}
}
for (char i = 0; i < (sizeof(dataStore) / sizeof(dataStore[0])); i++)
{
Serial.println(dataStore[i],BIN);
}
}
void loop()
{
// put your main code here, to run repeatedly:
}
I tested this code as is working for alternating ones and zeros at a bit level for data store defined as boolean
, byte
, and unsigned long
. Probably works for all the other datatypes as well. (The results of boolean
looks the same as byte
.)