formatting buffers

Y

yuvalif

I want to get rid of my "sprintf" call, so I wrote the following
example, in which I have two problems:
(1) why do I need to inherit from "streambuf", and not just use it as a
local in my "ToBuff" function (I get a protected constructor error)?
(2) I fail to get the output of the formatting in my C buffer, the
output of the program is:
string is: 100
buffer is: hello world
When I hoped to get:
string is: 100
buffer is: 100

note: the "ToString" function is not a real option where large buffers
should be allocated outside the class in "C style" code

the code:
///////////////////////////////////////////////////////////
#include <ostream>
#include <sstream>
#include <stdio.h>
#include <iostream>
using namespace std;

template <typename T>
class A : public streambuf
{
public:
A(const T& t) : m_value(t) {}

char* ToBuff(char* szBuff, int nSize)
{
pubsetbuf(szBuff, static_cast<streamsize>(nSize));
ostream os(this);
os << m_value << ends;
return szBuff;
}

string ToString() const
{
ostringstream ost(ostringstream::eek:ut);
ost << m_value << ends;
return ost.str();
}

private:
T m_value;
};

int main()
{
char buff[32]="hello world";

A<double> a(99.99999);

cout << "string is: " << a.ToString() << endl;
printf("buffer is: %s\n", a.ToBuff(buff,32));

return 0;
}
 
J

John Harrison

yuvalif said:
I want to get rid of my "sprintf" call, so I wrote the following
example, in which I have two problems:
(1) why do I need to inherit from "streambuf", and not just use it as a
local in my "ToBuff" function (I get a protected constructor error)?
(2) I fail to get the output of the formatting in my C buffer, the
output of the program is:
string is: 100
buffer is: hello world
When I hoped to get:
string is: 100
buffer is: 100

note: the "ToString" function is not a real option where large buffers
should be allocated outside the class in "C style" code

the code:
///////////////////////////////////////////////////////////
#include <ostream>
#include <sstream>
#include <stdio.h>
#include <iostream>
using namespace std;

template <typename T>
class A : public streambuf
{
public:
A(const T& t) : m_value(t) {}

char* ToBuff(char* szBuff, int nSize)
{
pubsetbuf(szBuff, static_cast<streamsize>(nSize));
ostream os(this);
os << m_value << ends;
return szBuff;
}

string ToString() const
{
ostringstream ost(ostringstream::eek:ut);

This is more simply written

ostringstream ost;
ost << m_value << ends;

No need for ends with streamstream. In fact it is incorrect, unless you
really do want a nul byte included in your C++ string.

ost << m_value;
return ost.str();
}

private:
T m_value;
};

int main()
{
char buff[32]="hello world";

A<double> a(99.99999);

cout << "string is: " << a.ToString() << endl;
printf("buffer is: %s\n", a.ToBuff(buff,32));

return 0;
}

Basically you are misusing streambuf. It's designed as a base for stream
buffers, not for converting values to strings. The class you do need is
ostrstream.

#include <strstream>

char* ToBuff(char* szBuff, int nSize)
{
ostrstream ost(szBuff, nSize);
ost << m_value << ends;
return szBuff;
}

Don't much like your class design either, I would make these two
template functions.

template <class T>
string toString(const T& x)
{
...
}

template <class T>
char* toBuffer(const T& x, char* buf, int size)
{
...
}

Seems easier to use to me.

All code untested.

john
 
Y

yuvalif

thanks john, working fine.

Two questions:
(1) My compiler (gcc4.0) warn me that: <strstream> is depreciated, any
idea for another include?
(2) Regarding the design, if I already have a template class, why
shouldn't it have a member function for the conversion?

Yuval.
 
J

John Harrison

yuvalif said:
thanks john, working fine.

Two questions:
(1) My compiler (gcc4.0) warn me that: <strstream> is depreciated, any
idea for another include?

It is deprecated, but personally I wouldn't worry. It still has
legitimate uses. But if you really want to avoid it then I would try
something like this

char* ToBuff(char* szBuff, int nSize)
{
ToString().copy(szBuff, nSize);
return szBuff;
}

In fact maybe that is preferable anyway.

(2) Regarding the design, if I already have a template class, why
shouldn't it have a member function for the conversion?

I was suggesting that you replace the template class with two template
functions. But if you have the template class already for other reasons
then fine.

john
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,769
Messages
2,569,580
Members
45,054
Latest member
TrimKetoBoost

Latest Threads

Top