itoa

M

Mark

hi,
all i want is a simple function that takes an int, and returns a char*

so i tried

char * itoa(int i)
{
char buff[35];
return _itoa(i,buff,10);
}

but all it spits out is jibberish.
i don't understand why it's so necessary to have to pass in a c-string,
use a function to modify it, and then print it. it makes it highly
irritating when i want to do something like

printf("%s", itoa(my_int));

but noo...! instead i have to do

char my_string[32];
itoa(my_int,my_string,10);
printf("%s, my_string);

blah.

anyways... i'm sure there's a solution out there. does anyone know it?
 
P

Peter Jansson

Mark said:
hi,
all i want is a simple function that takes an int, and returns a char*

so i tried

char * itoa(int i)
{
char buff[35];
return _itoa(i,buff,10);
}

but all it spits out is jibberish.
i don't understand why it's so necessary to have to pass in a c-string,
use a function to modify it, and then print it. it makes it highly
irritating when i want to do something like

printf("%s", itoa(my_int));

but noo...! instead i have to do

char my_string[32];
itoa(my_int,my_string,10);
printf("%s, my_string);

blah.

anyways... i'm sure there's a solution out there. does anyone know it?

How about the C++ faq:
http://www.parashift.com/c++-faq-lite/misc-technical-issues.html

Regards,
Peter Jansson
 
M

Mark

kind of an ugly round-about solution, but it works; thanks

const char * itoa(int i)
{
ostringstream o;
o << i;
return o.str().c_str();
}

dont think i should have to use std:strings so that i can return a
char* though.
 
M

Mark

kind of an ugly round-about solution, but it works; thanks

const char * itoa(int i)
{
ostringstream o;
o << i;
return o.str().c_str();
}

dont think i should have to use std:strings so that i can return a
char* though.
 
M

Mark

hm.. the problem i'm having is that when i do

printf("Kill %s %s for %s at '%s'.", act.units == 0 ? "all" :
itoa(act.units), getUnit(act.score), getGroup(act.group1),
itoa(act.location));

it prints "24" as the location, when it should be "64".
note that act.group1 is 24.

(yes there is a reason im using %s instead of %i or %d, but %i does fix
the problem...)
 
M

Mark

errr... nvm. it must be a problem with printf. if you do something like

printf("%s %s %s",itoa,itoa,itoa) it will always take the first one for
all 3.
 
M

Mark

i'd just like to point out how frusterated and disappointed i am with
c++ at the moment.
java would not give me a single problem with this. i had to rewrite

printf("Kill %s %s for %s at '%s'.", act.units == 0 ? "all" :
itoa(act.units), getUnit(act.score), getGroup(act.group1),
itoa(act.location));

to

cout << "Kill ";
if(act.units == 0) cout << "all";
else cout << (int)act.units;
cout << " " << getUnit(act.score) << " for " <<
getGroup(act.group1) << " at '" << act.location << "'.";

because apparently the ? operator cant mix and match return types, nor
can the << operator combine ints, or even chars with c-strings.

it's so ugly >.< just to do something so simple!!!
 
A

atgraham

You shouldn't let your ignorance cloud your judgement. Java is a very
different language than C or C++. You obviously don't understand how
memory is used/allocated. If you're an amateur programmer and you
don't want to learn C++, then stick with Java. If you wish to learn
C++, then people (I anyway) will be happy to help you.
 
K

Kyle

Mark napisał(a):
kind of an ugly round-about solution, but it works; thanks

const char * itoa(int i)
{
ostringstream o;
o << i;
return o.str().c_str();
}

you return a pointer into some buffer (associated with 'o') here, but
that buffer no longer exist after function returns

the simplest way to avoid the problem here is to return std::string from
the function - it carrys a buffer in itself

std::string itoa(int i) {
ostringstream o;
o << i;
return o.str();
}
dont think i should have to use std:strings so that i can return a

you should, unless you want to provide your own buffor, which you will
need to pass to the function, or (bad idea) create dynamically (with
new/malloc etc ...) inside the function (and destroy when appropriate
), but than you got more problems with buffor size ...
 
P

Peter Jansson

Mark said:
i'd just like to point out how frusterated and disappointed i am with
c++ at the moment.
java would not give me a single problem with this. i had to rewrite

printf("Kill %s %s for %s at '%s'.", act.units == 0 ? "all" :
itoa(act.units), getUnit(act.score), getGroup(act.group1),
itoa(act.location));

to

cout << "Kill ";
if(act.units == 0) cout << "all";
else cout << (int)act.units;
cout << " " << getUnit(act.score) << " for " <<
getGroup(act.group1) << " at '" << act.location << "'.";

because apparently the ? operator cant mix and match return types, nor
can the << operator combine ints, or even chars with c-strings.

it's so ugly >.< just to do something so simple!!!

Hi,

I have no comment about the beauty of the code but I guess your problem
was solved?

Regards,
Peter Jansson
 
G

Gernot Frisch

Mark said:
errr... nvm. it must be a problem with printf. if you do something
like

printf("%s %s %s",itoa,itoa,itoa) it will always take the first one
for
all 3.

Sure, because itoa has a static buffer for these operations. It
returns you the same address all the time.
If you want it this way, you have to return a std::string and use
their .c_str() member like this:


std::string xitoa(int i)
{
ostringstream o;
o << i;
return o.str()
}

printf("%s, %s", xitoa(15).c_str(), xitoa(25).c_str() );
 
L

Luke Meyers

Mark said:
i'd just like to point out how frusterated and disappointed i am with
c++ at the moment.
java would not give me a single problem with this.

There's no question that C++ can be frustrating, most especially to
beginners. Even more so to those who have been previously sold on the
easy get-up-and-go of a language like Java. But if you're serious
about programming with a truly powerful and expressive tool, stick with
it and don't be so easily discouraged. The fact is, C++ is such a
flexible language, pretty much all the "easy to use" idioms from Java
or wherever could be implemented as libraries.

But the base language, and the standard C and C++ libraries, have their
reasons for being the way they are. When you get done being
frustrated, take a moment and get educated about why things are the way
they are. You may find, as many of us have, that from the perspective
of a professional software engineer, some of these decisions are
incredibly shrewd and elegant, once you get into the appropriate
mindset to appreciate them.

Read a book or three. Koenig and Moo's "Accelerated C++" is widely
recommended. I'd also suggest you add Stroustrup's "The Design and
Evolution of C++;" it's not a language tutorial, but rather a sort of
history of how and why the language has developed the way it has.
Understanding the principles upon which it operates can help one get
into that mindset, and avoid much frustration. It's also a very
enjoyable read (I'm about halfway through it myself at the moment, just
got it a few days ago).

And if reading, gasp, *multiple* books seems like too much effort...
well, stick with Java. I use both languages professionally, and IMHO
there's really no comparison. Java's great for many things, but C++
tends to be a preferable choice for the really interesting problems.
It's harder to master, sure... but while calculus is harder to master
than arithmetic, if all you ever learn is arithmetic you're not going
to be much of a mathematician.

Luke
 
G

Gavin Deane

Mark said:
kind of an ugly round-about solution, but it works; thanks

const char * itoa(int i)
{
ostringstream o;
o << i;
return o.str().c_str();
}


The approach in the FAQ is

std::string itoa(int i)
{
std::eek:stringstream o;
o << i;
return o.str();
}

That's a huge difference. This returns a std::string by value, which is
a *copy* of the string in the ostringstream.

Your version returns a pointer to the char* data of the string in the
ostringstream. That pointer is valid only as long as the string exists
and is not modifed. After the function returns, the ostringstream and
the string in it, having automatic storage duration, are destroyed.

Because the pointer returned by the function points into nowhere,
dereferencing it has undefined behaviour. It seems that you were
unlucky and got exactly the behaviour you wanted. Undefined behaviour
means that anything can happen, including, unfortunately, just what you
expect.
dont think i should have to use std:strings so that i can return a
char* though.

I don't think you should have to use char* just to return a string.

char* is a seriously low level tool for representing and working with
strings. If you want to use the low level tool, you have to be prepared
to take manual responsibilty for the low level memory management
required.

If you don't want that responsibility, and for general use of strings
in C++ you almost never do, then use std::string. That's what it's for.

Gavin Deane
 
M

Mark

well, ok, i could use std::strings, but printf won't accept them, so i
have to convert them where ever i want to use them, right?

and i don't really like all these assumptions about me being new to
C++. yes, i understand where that's coming from, but i've used C++ for
a couple years, unfortunately without any proper instruction.

i've learnt the basics in school, and the rest i've taught myself.
needless to say, the teacher never really covered pointers and such.
i've mostly spent my time teaching myself game design, on a need to
know basis. when i run into a problem, i run out and find the
solution, and thus i'm constantly learning.

i just completed my first semester in university... in which i had to
learn Java. i wasn't keen on it at first, thinking C++ was
superior..but grudgingly i think i gave into some of Java's simplicity
of string handling.

i've always tried to advoid std:strings and other libraries i didn't
program myself... always thinking there is too much baggage, or they
aren't compatible with other functions and such.

anyways... that's my story.

http://groups.google.com/group/comp.lang.c++/msg/6f4ab6951b54236d

so.. by making it static, the buffer data is sort of "locked" in
memory, and thus it doesnt get overwritten or lost when the function
returns. thus our pointer will still point to meaningful data,
correct?

running this quick test,

#include <cstdlib>
#include <iostream>

using namespace std;

char * itoa(int i)
{
static char buff[35];
return _itoa(i,buff,10);



}

int main(int argc, char *argv[])
{
printf("%s %s %s", itoa(1), itoa(2), itoa(3));
system("PAUSE");
return EXIT_SUCCESS;
}

it prints "1 1 1"

now if i'm not mistaken, since the buffer is in the same memory
location each time the function is called (because it's static)... all
3 pointers should point to the same location in memory, which is
probably why they are printing the same thing.

now what i'm thinking really happens, is that itoa is called 3 times,
the pointers are returned, and THEN the "%s %s %s" is evaluated, using
what happens to be the same pointer, rather than evaluating each %s and
corresponding parameter at the same time....

which all makes very good sense to me now. i feel clever for figuring
that out .. i hope i'm right :D

lol.

so i'm thinking
http://groups.google.com/group/comp.lang.c++/msg/df3e00fcce160384 would
be my best solution? (xitoa)

are there any other print functions that actually take std:strings as
parameters?
or is there a way i could do "my string" + 5 + my_other_string?
 
J

James Juno

Mark said:
well, ok, i could use std::strings, but printf won't accept them, so i
have to convert them where ever i want to use them, right?

and i don't really like all these assumptions about me being new to
C++. yes, i understand where that's coming from, but i've used C++ for
a couple years, unfortunately without any proper instruction.

i've learnt the basics in school, and the rest i've taught myself.
needless to say, the teacher never really covered pointers and such.
i've mostly spent my time teaching myself game design, on a need to
know basis. when i run into a problem, i run out and find the
solution, and thus i'm constantly learning.

i just completed my first semester in university... in which i had to
learn Java. i wasn't keen on it at first, thinking C++ was
superior..but grudgingly i think i gave into some of Java's simplicity
of string handling.

i've always tried to advoid std:strings and other libraries i didn't
program myself... always thinking there is too much baggage, or they
aren't compatible with other functions and such.

anyways... that's my story.

http://groups.google.com/group/comp.lang.c++/msg/6f4ab6951b54236d

so.. by making it static, the buffer data is sort of "locked" in
memory, and thus it doesnt get overwritten or lost when the function
returns. thus our pointer will still point to meaningful data,
correct?

running this quick test,

#include <cstdlib>
#include <iostream>

using namespace std;

char * itoa(int i)
{
static char buff[35];
return _itoa(i,buff,10);



}

int main(int argc, char *argv[])
{
printf("%s %s %s", itoa(1), itoa(2), itoa(3));
system("PAUSE");
return EXIT_SUCCESS;
}

it prints "1 1 1"

now if i'm not mistaken, since the buffer is in the same memory
location each time the function is called (because it's static)... all
3 pointers should point to the same location in memory, which is
probably why they are printing the same thing.

now what i'm thinking really happens, is that itoa is called 3 times,
the pointers are returned, and THEN the "%s %s %s" is evaluated, using
what happens to be the same pointer, rather than evaluating each %s and
corresponding parameter at the same time....

which all makes very good sense to me now. i feel clever for figuring
that out .. i hope i'm right :D

lol.

so i'm thinking
http://groups.google.com/group/comp.lang.c++/msg/df3e00fcce160384 would
be my best solution? (xitoa)

are there any other print functions that actually take std:strings as
parameters?
or is there a way i could do "my string" + 5 + my_other_string?

OK, I'm nitpicking, but please take this on a constructive note: Don't
type like you are conversing through an IM client. Use capitalization
and proper punctuation and the like, and you're bound to be taken more
seriously. Improper use of things like this indicate you are speaking
down to your reader --- as if he/she is not worth your effort to reach
over and hit the shift key now and then.

Thanks,
-JJ
 
M

Mark

It's my style. Books can be written in this nature, I don't understand
why a post can't.
I do appreciate your comments, but it is a bit like a conversation,
isn't it?
But perhaps I shall try to clean up my posts from this point forth. I
understand that you are not the only person with that opinion.
 
R

Ron Natalie

Mark said:
well, ok, i could use std::strings, but printf won't accept them, so i
have to convert them where ever i want to use them, right?

Who says you need to use printf? And you can extract a char* form
std::string using the c_str().
and i don't really like all these assumptions about me being new to
C++. yes, i understand where that's coming from, but i've used C++ for
a couple years, unfortunately without any proper instruction.

Your new then. If you weren't new you'd not be asking these questions.
i've always tried to advoid std:strings and other libraries i didn't
program myself... always thinking there is too much baggage, or they
aren't compatible with other functions and such.

Making tons of mistakes in your programming reinventing what the
implementation is required to provide is BAGGAGE.
so.. by making it static, the buffer data is sort of "locked" in
memory, and thus it doesnt get overwritten or lost when the function
returns. thus our pointer will still point to meaningful data,
correct?

You're not new and you don't know what "static" means?

Yes static storage means that it won't go away when the function
returns. There exists exactly one copy of that static variable
that is used for all invocations of the function. If you were
to print out the poitner, that itoa is returning you'll see it
is always the same value.


Exactly what we've been telling you. It uses std::string which unlike
char* IS A STRING TYPE.

You could do
printf("%s %s %s", xitoa(1).c_str(), xitoa(2).c_str(), xitoa(3).c_str());

If you really need to pass the result to printf.
are there any other print functions that actually take std:strings as
parameters?
or is there a way i could do "my string" + 5 + my_other_string?

Yes, look at what xitoa does internally:

ostringstream os;
os << "my string" << 5 << my_other_string;
return os.str();

An ostringstream builds up a string that contains the things you output
to it just as if you were outputing to say cout. The str() method
returns a copy of that internal string.
 
M

Mark

Ron said:
Who says you need to use printf? And you can extract a char* form
std::string using the c_str().


Your new then. If you weren't new you'd not be asking these questions.


Making tons of mistakes in your programming reinventing what the
implementation is required to provide is BAGGAGE.


You're not new and you don't know what "static" means?

Yes static storage means that it won't go away when the function
returns. There exists exactly one copy of that static variable
that is used for all invocations of the function. If you were
to print out the poitner, that itoa is returning you'll see it
is always the same value.



Exactly what we've been telling you. It uses std::string which unlike
char* IS A STRING TYPE.

You could do
printf("%s %s %s", xitoa(1).c_str(), xitoa(2).c_str(), xitoa(3).c_str());

If you really need to pass the result to printf.

Yes, look at what xitoa does internally:

ostringstream os;
os << "my string" << 5 << my_other_string;
return os.str();

An ostringstream builds up a string that contains the things you output
to it just as if you were outputing to say cout. The str() method
returns a copy of that internal string.

I meant other than ostringstream, but I guess that should work fine.
No more questions.
 
G

Gavin Deane

Mark said:
well, ok, i could use std::strings, but printf won't accept them, so i
have to convert them where ever i want to use them, right?

Not if you do you input and output using streams (like cin and cout) -
see below.

i've always tried to advoid std:strings and other libraries i didn't
program myself... always thinking there is too much baggage, or they
aren't compatible with other functions and such.

The facilities of the C++ standard library (strings, streams,
containers, algorithms, etc.) are fully compatible with each other by
design and provide commonly needed functionality out of the box.

running this quick test,

#include <cstdlib>
#include <iostream>

using namespace std;

char * itoa(int i)
{
static char buff[35];
return _itoa(i,buff,10);
}

int main(int argc, char *argv[])
{
printf("%s %s %s", itoa(1), itoa(2), itoa(3));
system("PAUSE");
return EXIT_SUCCESS;
}

it prints "1 1 1"

now if i'm not mistaken, since the buffer is in the same memory
location each time the function is called (because it's static)... all
3 pointers should point to the same location in memory, which is
probably why they are printing the same thing.

now what i'm thinking really happens, is that itoa is called 3 times,
the pointers are returned, and THEN the "%s %s %s" is evaluated, using
what happens to be the same pointer, rather than evaluating each %s and
corresponding parameter at the same time....

which all makes very good sense to me now. i feel clever for figuring
that out .. i hope i'm right :D

Yes you are right. All the arguments to a function are fully evaluated
_before_ the function itself is called. Parsing "%s %s %s" and
inserting the character sequences obtained by dereferencing the pointer
arguments happens _inside_ the printf function, so by the time it
happens, the three itoa calls are complete.

So what actually gets printed is whatever was stored in the buffer by
the last of the three calls to itoa. In your case, the last call must
have been itoa(1). That's allowed - the compiler does not have to
evaluate the function arguments in the order they apppear in your code.
It can evaluate them in any order it likes.
are there any other print functions that actually take std:strings as
parameters?
or is there a way i could do "my string" + 5 + my_other_string?

#include <string>
#include <iostream>

int main()
{
std::string my_other_string = "my other string";
std::cout << "my string" << 5 << my_other_string << "\n";

return 0;
}

Gavin Deane
 

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,055
Latest member
SlimSparkKetoACVReview

Latest Threads

Top