Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > C++ > How can I better manage strings and memory

Reply
Thread Tools

How can I better manage strings and memory

 
 
DeveloperDave
Guest
Posts: n/a
 
      10-19-2008
Hi,

I am trying to improve some code that I currently have.

I have a simple class called RequestMessage e.g.

class RequestMessage
{
public:
RequestMessage();
~RequestMessage();

string& getMessage()

private:
string origin
string type;
string body;
....
....
string rqstMessage;
};

getMessage formats the private members and stores them in rqstMessage
before returning a reference to it.

string&
RequestMessage::getMessage()
{
ostringstream* message = new ostringstream("Orgin: ");
message << origin << endl;
message << "Type:" << type << endl;
message << "Body: << body << endl;

rqstMessage = message->str();

return rqstMessage;
}

The problem I have, is that I don't like the fact I already have
stored my data in strings, and then use another string to store it all
again in a formatted way.
Is there a better way to do this, without using the additional memory?

Cheers



 
Reply With Quote
 
 
 
 
Gennaro Prota
Guest
Posts: n/a
 
      10-19-2008
DeveloperDave wrote:
> Hi,
>
> I am trying to improve some code that I currently have.
>
> I have a simple class called RequestMessage e.g.
>
> class RequestMessage
> {
> public:
> RequestMessage();
> ~RequestMessage();
>
> string& getMessage()
>
> private:
> string origin
> string type;
> string body;
> ....
> ....
> string rqstMessage;
> };
>
> getMessage formats the private members and stores them in rqstMessage
> before returning a reference to it.
>
> string&
> RequestMessage::getMessage()
> {
> ostringstream* message = new ostringstream("Orgin: ");
> message << origin << endl;
> message << "Type:" << type << endl;
> message << "Body: << body << endl;
>
> rqstMessage = message->str();
>
> return rqstMessage;
> }
>
> The problem I have, is that I don't like the fact I already have
> stored my data in strings, and then use another string to store it all
> again in a formatted way.
> Is there a better way to do this, without using the additional memory?


It would be important to know the context. Anyhow, first be sure
you don't leak the "additional memory" for the ostringstream
(this is not Java). Then, what's the role of rqstMessage? Is it
a cache? Did you make measurements that show you *need* it? If
so make it a mutable member and make getMessage() const.
Otherwise just forget about it, and return a string instead of a
reference.

--
Gennaro Prota | name.surname yahoo.com
Breeze C++ (preview): <https://sourceforge.net/projects/breeze/>
Do you need expertise in C++? I'm available.
 
Reply With Quote
 
 
 
 
red floyd
Guest
Posts: n/a
 
      10-19-2008
DeveloperDave wrote:
> Hi,
>
> I am trying to improve some code that I currently have.
>
> I have a simple class called RequestMessage e.g.
>
> class RequestMessage
> {
> public:
> RequestMessage();
> ~RequestMessage();
>
> string& getMessage()
>
> private:
> string origin
> string type;
> string body;
> ....
> ....
> string rqstMessage;
> };
>
> getMessage formats the private members and stores them in rqstMessage
> before returning a reference to it.
>
> string&
> RequestMessage::getMessage()
> {
> ostringstream* message = new ostringstream("Orgin: ");
> message << origin << endl;
> message << "Type:" << type << endl;
> message << "Body: << body << endl;
>
> rqstMessage = message->str();
>
> return rqstMessage;
> }


This is a memory leak. Why are you newing message? And why are you not
deleteing it? It should simply be declared as a local variable:

ostringstream message;

Let me guess, you're coming from Java?
 
Reply With Quote
 
DeveloperDave
Guest
Posts: n/a
 
      10-19-2008
On Oct 19, 7:34*pm, red floyd <(E-Mail Removed)> wrote:
> DeveloperDave wrote:
> > Hi,

>
> > I am trying to improve some code that I currently have.

>
> > I have a simple class called RequestMessage e.g.

>
> > class RequestMessage
> > {
> > public:
> > * * RequestMessage();
> > * * ~RequestMessage();

>
> > * *string& getMessage()

>
> > private:
> > * *string origin
> > * *string type;
> > * *string body;
> > * *....
> > * *....
> > * string rqstMessage;
> > };

>
> > getMessage formats the private members and stores them in rqstMessage
> > before returning a reference to it.

>
> > string&
> > RequestMessage::getMessage()
> > {
> > * *ostringstream* message = new ostringstream("Orgin: ");
> > * *message << origin << endl;
> > * *message << "Type:" << type << endl;
> > * *message << "Body: *<< body << endl;

>
> > * *rqstMessage = *message->str();

>
> > * *return rqstMessage;
> > }

>
> This is a memory leak. *Why are you newing message? *And why are you not
> deleteing it? *It should simply be declared as a local variable:
>
> * *ostringstream message;
>
> Let me guess, you're coming from Java?


Guys, I'm not coming from java, and I don't want to know that I should
always call delete with new (I know this already). This also isn't
the final code, it is an example to illustrate my problem. Why not
comment that the "..." will cause the code not to compile as well?

The question is:

is it possible to use the member variables to construct a formatted
string, i.e.
Something like

"Orgin:%s\nType:%s\nBody:%s\n"

Replacing the %s with my member variables, "orgin", "type", and
"body", but without storing these in a new string i.e. not storing the
same information twice.
 
Reply With Quote
 
AnonMail2005@gmail.com
Guest
Posts: n/a
 
      10-19-2008
On Oct 19, 12:29*pm, DeveloperDave <(E-Mail Removed)> wrote:
> Hi,
>
> I am trying to improve some code that I currently have.
>
> I have a simple class called RequestMessage e.g.
>
> class RequestMessage
> {
> public:
> * * RequestMessage();
> * * ~RequestMessage();
>
> * *string& getMessage()
>
> private:
> * *string origin
> * *string type;
> * *string body;
> * *....
> * *....
> * string rqstMessage;
>
> };
>
> getMessage formats the private members and stores them in rqstMessage
> before returning a reference to it.
>
> string&
> RequestMessage::getMessage()
> {
> * *ostringstream* message = new ostringstream("Orgin: ");
> * *message << origin << endl;
> * *message << "Type:" << type << endl;
> * *message << "Body: *<< body << endl;
>
> * *rqstMessage = *message->str();
>
> * *return rqstMessage;
>
> }
>
> The problem I have, is that I don't like the fact I already have
> stored my data in strings, and then use another string to store it all
> again in a formatted way.
> Is there a better way to do this, without using the additional memory?
>
> Cheers


Without context, it's hard to say. But why not build the message
in a constructor so that the arguments to the contructor are the
components and only one copy of the built message is kept within
the class.

HTH
 
Reply With Quote
 
Thomas J. Gritzan
Guest
Posts: n/a
 
      10-19-2008
DeveloperDave wrote:
> On Oct 19, 7:34 pm, red floyd <(E-Mail Removed)> wrote:
>> This is a memory leak. Why are you newing message? And why are you not
>> deleteing it? It should simply be declared as a local variable:
>>
>> ostringstream message;
>>
>> Let me guess, you're coming from Java?

>
> Guys, I'm not coming from java, and I don't want to know that I should
> always call delete with new (I know this already). This also isn't
> the final code, it is an example to illustrate my problem. Why not
> comment that the "..." will cause the code not to compile as well?


The point wasn't to use delete, but not using 'new' at all for a
variable that is only locally used. If you 'new' the ostringstream,
there's no point in avoiding the string copy.

> The question is:
>
> is it possible to use the member variables to construct a formatted
> string, i.e.
> Something like
>
> "Orgin:%s\nType:%s\nBody:%s\n"


Yes,

> Replacing the %s with my member variables, "orgin", "type", and
> "body", but without storing these in a new string i.e. not storing the
> same information twice.


Without storing the complete string? That depends on what you want to do
with the string.

For only outputting it to console (or file), you could implement a print
function that outputs to ostream&:

RequestMessage:rint(std:stream& message) const
{
message << origin << '\n'
<< "Type:" << type << '\n'
<< "Body:" << body << endl;
}

That way, a client could pretty print the object to cout, to a file
stream, a memory stream or any other custom stream.

--
Thomas
 
Reply With Quote
 
Ian Collins
Guest
Posts: n/a
 
      10-19-2008
DeveloperDave wrote:
>
> The question is:
>
> is it possible to use the member variables to construct a formatted
> string, i.e.
> Something like
>
> "Orgin:%s\nType:%s\nBody:%s\n"
>
> Replacing the %s with my member variables, "orgin", "type", and
> "body", but without storing these in a new string i.e. not storing the
> same information twice.


That all depends on what you want to do with the result. If you just
want to output it, then follow Thomas' advice. But don't forget the
data probably will be stored twice because the output stream is buffered!

--
Ian Collins
 
Reply With Quote
 
red floyd
Guest
Posts: n/a
 
      10-19-2008
DeveloperDave wrote:
> On Oct 19, 7:34 pm, red floyd <(E-Mail Removed)> wrote:
>> DeveloperDave wrote:
>>> Hi,
>>> I am trying to improve some code that I currently have.
>>> I have a simple class called RequestMessage e.g.
>>> class RequestMessage
>>> {
>>> public:
>>> RequestMessage();
>>> ~RequestMessage();
>>> string& getMessage()
>>> private:
>>> string origin
>>> string type;
>>> string body;
>>> ....
>>> ....
>>> string rqstMessage;
>>> };
>>> getMessage formats the private members and stores them in rqstMessage
>>> before returning a reference to it.
>>> string&
>>> RequestMessage::getMessage()
>>> {
>>> ostringstream* message = new ostringstream("Orgin: ");
>>> message << origin << endl;
>>> message << "Type:" << type << endl;
>>> message << "Body: << body << endl;
>>> rqstMessage = message->str();
>>> return rqstMessage;
>>> }

>> This is a memory leak. Why are you newing message? And why are you not
>> deleteing it? It should simply be declared as a local variable:
>>
>> ostringstream message;
>>
>> Let me guess, you're coming from Java?

>
> Guys, I'm not coming from java, and I don't want to know that I should
> always call delete with new (I know this already). This also isn't
> the final code, it is an example to illustrate my problem. Why not
> comment that the "..." will cause the code not to compile as well?
>

Frankly, it doesn't matter. Your code flat out will not work.

ostreamstring *ss = new ostreamstring("origin: ");
ss << "Hello";

Will *NOT* work. There is no operator<< defined which takes a
ostreamstring* as a left hand side.


 
Reply With Quote
 
Gennaro Prota
Guest
Posts: n/a
 
      10-19-2008
DeveloperDave wrote:
> On Oct 19, 7:34 pm, red floyd <(E-Mail Removed)> wrote:
>> DeveloperDave wrote:
>>> Hi,
>>> I am trying to improve some code that I currently have.
>>> I have a simple class called RequestMessage e.g.
>>> class RequestMessage
>>> {
>>> public:
>>> RequestMessage();
>>> ~RequestMessage();
>>> string& getMessage()
>>> private:
>>> string origin
>>> string type;
>>> string body;
>>> ....
>>> ....
>>> string rqstMessage;
>>> };
>>> getMessage formats the private members and stores them in rqstMessage
>>> before returning a reference to it.
>>> string&
>>> RequestMessage::getMessage()
>>> {
>>> ostringstream* message = new ostringstream("Orgin: ");
>>> message << origin << endl;
>>> message << "Type:" << type << endl;
>>> message << "Body: << body << endl;
>>> rqstMessage = message->str();
>>> return rqstMessage;
>>> }

[...]
> The question is:
>
> is it possible to use the member variables to construct a formatted
> string, i.e.
> Something like
>
> "Orgin:%s\nType:%s\nBody:%s\n"
>
> Replacing the %s with my member variables, "orgin", "type", and
> "body", but without storing these in a new string i.e. not storing the
> same information twice.


You don't need to store the result into a data member, at all.
For most purposes, outputting to a stream is the best solution,
which you can do as suggested by Thomas or, more idiomatically,
writing your own stream inserter (operator <<). Of course, too,
the inserter may just forward the work to print(std:stream &).
In short, if you are formatting then use the C++ idioms for
formatting.

Otherwise, for the simple need you ask about, you can just
concatenate:

// note: not compiled
std::string
RequestMessage::getMessage() const
{
return "Orgin:" /*[sic]*/ + m_origin + "\n"
+ "Type:" + m_type + "\n"
+ "Body:" + m_body + "\n"
;
}

It's not an approach which defies the centuries but it's an
approach

If this doesn't answer your question you have to give us more
details.

--
Gennaro Prota | name.surname yahoo.com
Breeze C++ (preview): <https://sourceforge.net/projects/breeze/>
Do you need expertise in C++? I'm available.
 
Reply With Quote
 
DeveloperDave
Guest
Posts: n/a
 
      10-19-2008
On Oct 19, 10:49*pm, Gennaro Prota <gennaro/(E-Mail Removed)> wrote:
> DeveloperDave wrote:
> > On Oct 19, 7:34 pm, red floyd <(E-Mail Removed)> wrote:
> >> DeveloperDave wrote:
> >>> Hi,
> >>> I am trying to improve some code that I currently have.
> >>> I have a simple class called RequestMessage e.g.
> >>> class RequestMessage
> >>> {
> >>> public:
> >>> * * RequestMessage();
> >>> * * ~RequestMessage();
> >>> * *string& getMessage()
> >>> private:
> >>> * *string origin
> >>> * *string type;
> >>> * *string body;
> >>> * *....
> >>> * *....
> >>> * string rqstMessage;
> >>> };
> >>> getMessage formats the private members and stores them in rqstMessage
> >>> before returning a reference to it.
> >>> string&
> >>> RequestMessage::getMessage()
> >>> {
> >>> * *ostringstream* message = new ostringstream("Orgin: ");
> >>> * *message << origin << endl;
> >>> * *message << "Type:" << type << endl;
> >>> * *message << "Body: *<< body << endl;
> >>> * *rqstMessage = *message->str();
> >>> * *return rqstMessage;
> >>> }

> * * *[...]
> > The question is:

>
> > is it possible to use the member variables to construct a formatted
> > string, i.e.
> > Something like

>
> > "Orgin:%s\nType:%s\nBody:%s\n"

>
> > Replacing the %s with my member variables, "orgin", "type", and
> > "body", but without storing these in a new string i.e. not storing the
> > same information twice.

>
> You don't need to store the result into a data member, at all.
> For most purposes, outputting to a stream is the best solution,
> which you can do as suggested by Thomas or, more idiomatically,
> writing your own stream inserter (operator <<). Of course, too,
> the inserter may just forward the work to print(std:stream &).
> In short, if you are formatting then use the C++ idioms for
> formatting.
>
> Otherwise, for the simple need you ask about, you can just
> concatenate:
>
> * *// note: not compiled
> * *std::string
> * *RequestMessage::getMessage() const
> * *{
> * * * *return "Orgin:" /*[sic]*/ + m_origin + "\n"
> * * * * * * * + "Type:" * * * * *+ m_type * + "\n"
> * * * * * * * + "Body:" * * * * *+ m_body * + "\n"
> * * * * * * * ;
> * *}
>
> It's not an approach which defies the centuries but it's an
> approach
>
> If this doesn't answer your question you have to give us more
> details.
>
> --
> * *Gennaro Prota * * * * | * * * * * name.surname yahoo.com
> * * *Breeze C++ (preview): <https://sourceforge.net/projects/breeze/>
> * * *Do you need expertise in C++? * I'm available.


Thanks for the constructive suggestions. I will eventually be writing
the data to a stream, so I guess passing that stream in writing to it,
is the best approach.
Cheers.
 
Reply With Quote
 
 
 
Reply

Thread Tools

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
Re: How include a large array? Edward A. Falk C Programming 1 04-04-2013 08:07 PM
There may be a much better way to manage artillery. Tobiah Python 4 05-11-2009 09:59 PM
Strings, Strings and Damned Strings Ben C Programming 14 06-24-2006 05:09 AM
How to manage information and resources on your own memory stick vmcontrol@gmail.com Computer Support 1 12-08-2005 02:53 PM
Build a Better Blair (like Build a Better Bush, only better) Kenny Computer Support 0 05-06-2005 04:50 AM



Advertisments