Ghani
Ghani

Reputation: 51

how to convert binary data to float value?

For my data logger project I'm logging data to a SD card. Here I'm storing the data in binary format. I'm logging accelerometer and temp&humidity sensors. I could read data byte by byte. Hence to print ADXL data (two bytes), I combine each two byte data. Hence four bytes has to be combined to get temparature data. Unfortunately for temparature I failed to print actual data. There is some conversion problem. I'm looking some help regarding how to convert data to floats.

Code to read and print binary to uint16_t ( accelerometer data): working

while ((nr = fgetc(logFile)) != EOF){
         pc.printf(" \r\n %d ",nr);
          acc_con[i] = nr;
          if (i == 1){ 
          acc = (acc_con[1]<<8) | acc_con[0];
          pc.printf(" \r\n %i ",acc);
          i = 0;} 
          else i++; 
         }

Code to read and print binary to float ( temparature data): Not working

while ((nr = fgetc(logFile)) != EOF){
         pc.printf(" \r\n %d ",nr);
           humicon[i] = nr;
           if (i == 3){
            hum = (humicon[0] << 24) | (humicon[1] << 16) | (humicon[2] << 8) | humicon[3];
            pc.printf(" \r\n %f ",hum);
            i = 0;}
            else i++;
            }

The byte by byte raw data from variable nr is: 24, 58, 46, 66, and the output from variable hum is: 406466112.000000.

I could read humidity or temparature (floats) with fread. Unfortunatly to use fread I must know th no of bytes stored in the file. With below code I could print floats also. int main() {

int nr;
FILE *fp = fopen("/sd/PCE000.bin", "rb");
float read[1];
fread(read,sizeof(float),1,fp);
pc.printf("\r\n %f",read[0]);
  fclose(fp); 

}

I would like to know the formula for the conversion like (acc_con[1]<<8) | acc_con[0]. Thank you.

Upvotes: 1

Views: 4286

Answers (3)

jurhas
jurhas

Reputation: 653

Yap, is not simple function, transform an array of bytes to a floating point function. I am lookin also to implement it to avoid portable reasons. There are differences also between little endian and big endian machines. But there are several hacks to this problem. First the file size, you have to include "sys/stat.h", with small differences is also portable. But is not required. Read it as buffer of char :

char f[sizeof(float)];
if (fread(f,1,sizeof(float), yourfile) ==sizeof(float))
{
    float *flt_ptr=f;
    printf("%f\n",*flt_ptr);
}

C is wonderful for those things, there is also no need to cast everithing.

Upvotes: 0

Rishikesh Raje
Rishikesh Raje

Reputation: 8614

With

unsigned int hum;
....
hum = (humicon[0] << 24) | (humicon[1] << 16) | (humicon[2] << 8) | humicon[3];

You are converting 8 bit data to 32 bit integer data. You can store this data directly. Or if you absolutely want to store in floats, you can use.

float hum_f;
....
hum_f = hum;

Upvotes: 0

unwind
unwind

Reputation: 399713

If you want to do this in Python, it sounds like a job for the struct module:

>>> struct.unpack("f", "".join([chr(x) for x in [24, 58, 46, 66]]))
(43.556732177734375,)

This assumes little-endian byte-order.

In C, you can use memcpy():

float x;
const unsigned char bytes[] = { 24, 58, 46, 66 };
memcpy(&x, bytes, sizeof x);
printf("%f\n", x);

Upvotes: 2

Related Questions