views:

274

answers:

2

I have a char array which contains null characters at random locations. I tried to create an iStringStream using this array (encodedData_arr) as below,

I use this iStringStream to insert binary data(imagedata of Iplimage) to a MySQL database blob field(using MySQL Connector/C++'s setBlob(istream *is) ) it only stores the characters upto the first null character.

Is there a way to create an iStringStream using a char array with null characters?

unsigned char *encodedData_arr = new unsigned char[data_vector_uchar->size()];
// Assign the data of vector<unsigned char> to the encodedData_arr
for (int i = 0; i < vec_size; ++i)
{
 cout<< data_vector_uchar->at(i)<< " : "<< encodedData_arr[i]<<endl;
}

// Here the content of the encodedData_arr is same as the data_vector_uchar
// So char array is initializing fine.
istream *is = new istringstream((char*)encodedData_arr, istringstream::in || istringstream::binary);

prepStmt_insertImage->setBlob(1, is);
// Here only part of the data is stored in the database blob field (Upto the first null character)
+3  A: 

There is nothing special about null characters in strings

std::istringstream iss(std::string(data, N));
setBlob(&iss);

Of course if you do

std::istringstream iss("haha a null: \0");

It will interpret that as a C-style string converted to std::string, and thus will stop at the \0, not taking it as a real content byte. Telling std::string the size explicitly allows it to consume any null byte as real content data.

If you want to read directly from a char array, you can use strstream

std::istrstream iss(data, N);

That will directly read from the data provided by data, up to N bytes. strstream is declared "deprecated" officially, but it's still going to be in C++0x, so you can use it. Or you create your own streambuf, if you really need to read from a raw char* like that.

struct myrawr : std::streambuf {
  myrawr(char const *s, size_t n) { 
    setg(const_cast<char*>(s), 
         const_cast<char*>(s), 
         const_cast<char*>(s + n));
  }
};

struct hasb { 
  hasb(char const *s, size_t n)
   :m(s, n)
  { }
  myrawr m;
};

// using base-from-member idiom
struct myrawrs : private hasb, std::istream {
  myrawrs(char const *s, size_t n)
    :hasb(s, n), 
     std::istream(&static_cast<hasb*>(this)->m)
  { }
};
Johannes Schaub - litb
A: 

// Here only part of the data is stored in the database blob field (Upto the first null character)

How are you checking this? If you are just dumping it to cout, its probably stopping at the first nul. You will need to print character by character.

KeithB