views:

53

answers:

2

I've created a small tool which is used to process binary files. All the functions involved in reading the files and processing them are templated and are similar to this:

template <class T> void processFile( const char* fileName );

The template parameter T is used to determine the size of data which will be read and treated as one item. I dont know how to say it precisely, so a tiny example (note that these are binary data as seen with a hexeditor). File contents:

BEEF1234DEAD5678

With T being unsigned char, items are: BE EF 12 34 DE AD 56 78
With T being unsigned int, items are: BEAF1234 DEAD5678
With T being a double: BEAF1234DEAD5678

(Note that I assume here that unsigned char is 1 byte, unsigned int is 4 bytes and double is 8 bytes large.) The T is also used for STL containers, because I use them a lot (a vector, a map and a list are used in many of the functions involved in processing files). Everything works perfectly fine with built-in datatypes (char, int etc.).

Now what is my problem: I would like to be able to work with sizes different from 1,4,8. For example 16, 32 or even 6, 10, 14 etc. As far as I know, there are no built-in types of these sizes. How can I achieve this? My main concern is that I need the data in STL containers and use sort() for example. Will a POD structure work? Note that I'm using mainly C functions for reading (no streams here, but some memcpy and memcmp, fread etc.).

Sorry for not providing more code, I'm using my spare laptop now. But i believe more code should not be necessary. If so, I will provide it tomorrow.

+2  A: 

If I understand your question correctly, the answer is yes: you should be able to specialize your template function with a suitable POD type. However you'll need to define a member operator<() in order to be able to use std::sort().

The following POD might be useful to you in the general case (it will certainly sort better than doubles):

template <int N>
struct MyFill{
  char contents[N];
  bool operator<(const MyFill<N>& other){
    for (int i=0; i<N; ++i){
      if (contents[i]!=other.contents[i]){
        return (contents[i]<other.contents[i]);
      }
    }
    return false;
  }
};
ssegvic
Thanks, this looks good!
PeterK
A: 

Use operator<< to extract data. This way the size of T and whether or not it can be sorted is not your problem. So get C++ streams, there's a reason we ditched fscanf for std::ifstream.

It's actually not safe to memcpy or memcmp many, many C++ types, and using them is a habit that you definitely should cut.

DeadMG