Click here to Skip to main content
15,899,026 members
Please Sign up or sign in to vote.
0.00/5 (No votes)
See more:
I have a binary file, a.txt, in the current path with:

3600 bytes - trace header
data blocks - each block has 400 datas

The data is of type "float".

My question is: how do I read the data blocks?

For example, I want to read the data in the first and also the second block. Can I use the following code?

...
float a[400][2];
...
FILE *fp;
fp=fopen("a.txt","r");
for(int i=0;i<2;i++)
{
  fseek=(fp,long(3600+i*400*4),0);
  for(int j=0;j<400;j++)
    fread(&a[j][i],4,400,fp);

}
...
Posted
Updated 6-Feb-10 3:56am
v3

If your file is actually in binary format ("a.txt" is really a bad name for a binary file), then you should skip the header and then read the data block at once.
float a[2][400];
FILE * fp = fopen("a.txt", "rb");
if (!fp)
{
  // handle error here
}
// skip header
if ( fseek(fp, 3600, SEEK_SET) )
{
  // handle error
} 
// read the first data block into the array 
if ( fread( &a[0][0], sizeof(float), 400, fp) != 400)
{
  // handle error
}
// if the second data block follows immediately, then you use
// the following statements. On the other hand, if there is
// first another header block, skip it before.
 
if ( fread( &a[1][0], sizeof(float), 400, fp) != 400)
{
  // handle error
}
 
Share this answer
 
v3
- When you want to read 2 blocks, use this array float a[2][400];.
- To read binary data, use binary mode in fopen().
- Use sizeof() for the number of array elements and size of one element. So when you change the size of the array or use another type you must not change the code for reading.
- Because an array in C is allready a pointer, you don't need the &-operator for a[i] in fread().
- When the data blocks are in serial order, you don't need a fseek() between the fread() calls. You even don't need a loop, you could read all data within one fread() call.
- The long(3600+i*400*4) is not a C typecast. It is a C++ copy constructor. This would compile in a C++ compiler but a C typecast is written (long)3600+i*400*4.
- Do some tests for error handling.

Finaly, it could look like this:
C#
float a[2][400];
FILE *fp = fopen( "a.txt","rb");
if( NULL != fp)
{
   size_t nElements = sizeof(a[0]) / sizeof(a[0][0]);
   for( int i=0; i<2; i++)
   {
      long lOffset = 3600 + i * sizeof(a[0]);
      if( 0 == fseek( fp, lOffset, SEEK_SET))
      {
         if( nElements != fread( a[i], sizeof(a[0][0]), nElements, fp))
         {
            // error handling
            break;
         }
      }
      else
      {
         // error handling
         break;
      }
   }
}
 
Share this answer
 
What happens when you run the code?

I'm not a C programmer but my C Quick Reference guide tells me that you are using the fread function incorrectly.

size_t fread(void *ptr, size_t size, size_t nmemb, FILE *stream);

Each invocation of fread in the inner loop is reading 400 data elements of size 4 bytes, i.e. 1600 bytes. I think you meant to write
fread(&a[j][i],4,1,fp);

There is also a syntax error in the line containing fseek which you'll need to correct before you can compile the code successfully.

Alan.
 
Share this answer
 
thank you all!
I have learned a lot!!
hehe,the next I will compile the code again!
Thank you all!
 
Share this answer
 

This content, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)



CodeProject, 20 Bay Street, 11th Floor Toronto, Ontario, Canada M5J 2N8 +1 (416) 849-8900