returning strings

M

MC felon

how do we return strings or arrays from a function? i tried..

char[] some_func() //where i thought char[] would tell the compiler
that the return is a string
{

char str[100];
//something;
return str;
}
thanks in advance!
 
G

Geo

MC said:
how do we return strings or arrays from a function? i tried..

char[] some_func() //where i thought char[] would tell the compiler
that the return is a string
{

char str[100];
//something;
return str;
}
thanks in advance!

You're writting C++ not C, do it like this

std::string some_func()
{
std::string str;
// something;
return str;
}
 
G

Gianni Mariani

MC said:
how do we return strings or arrays from a function? i tried..

char[] some_func() //where i thought char[] would tell the compiler
that the return is a string
{

char str[100];
//something;
return str;
}

That won't work too well since by the time the function returns the
value being returned is dead.

Did you read the FAQ?
 
M

MC felon

i work on TC++ (some old version). Please suggest something that works
in the same.
 
G

Gavin Deane

Rolf said:
It doesn't. You give it the memory, and the function fills it.

You give it the memory, and the function fills it, and the function
merrily continues filling memory past the end of the chunk you gave it
until the input is used up, and, unless your program has ABSOLUTE
control over the length of the input [*], there is absolutely nothing
you can do to prevent this risk.

To the OP: Don't use gets. If you are going to use C funcitons for
string input, use fgets.

[*] prompting the user to only type a certain number of characters is
by no means absolute control.

Gavin Deane
 
G

Gavin Deane

MC said:
i work on TC++ (some old version). Please suggest something that works
in the same.

Please quote enough of the message you are replying to to provide
context. On its own, your message is meaningless. To do that from
Google Groups, don't use the broken Reply link at the bottom of the
message. Instead, click the Show Options link at the top and use the
Reply link revealed there. Thanks.

To answer your question, did you #include<string>, the standard header
that defines the C++ string class (and puts it in namespace std)?

As to your compiler, if you can't get this

#include <string>
std::string some_func()
{
std::string str;
// something;
return str;
}

to compile, you haven't got a hope of learning or writing C++ with that
compiler. Fortunately, there are sevral up-to-date and free C++
compilers available for you to upgrade to. If you're on Windows,
Microsoft's VC++8 compiler is free for example, and there are other
options. If you're on a different platform there will, I am sure, be
other options too.

Gavin Deane
 
G

Geo

MC said:
i work on TC++ (some old version). Please suggest something that works
in the same.

Since I don't know what TC++ is, I don't know what works,. but if it
doesn't support the STL it isn't really C++ as I know it.

If you don't know how to work with C style strings, I suggest you read
a book, it's far to complicated to describe here.
 
M

MC felon

ok. thanks for the tip.
here's what i want the function to do.

allow the user to input a string. stop receiving input when user
presses tab.



its like gets, only that the input gets stopped when '\t' is pressed
and not '\r'.

how do i do this?
 
G

Geo

MC said:
ok. thanks for the tip.
here's what i want the function to do.

allow the user to input a string. stop receiving input when user
presses tab.



its like gets, only that the input gets stopped when '\t' is pressed
and not '\r'.

how do i do this?

You can't, not in staandard C++ anyway.
 
G

Gianni Mariani

Geo said:
You can't, not in staandard C++ anyway.

Strictly speaking, you can using "readsome()", but I would strongly
suggest not doing it that way.
 
G

Gavin Deane

MC said:
ok. thanks for the tip.
here's what i want the function to do.

allow the user to input a string. stop receiving input when user
presses tab.



its like gets, only that the input gets stopped when '\t' is pressed
and not '\r'.

how do i do this?

std::getline allows you to choose any delimiter character you want. The
default is newline but you can change that. This shows how it works.

#include <string>
#include <sstream>
#include <iostream>
using namespace std;

int main()
{
string input("abc\tdef\nghi");
istringstream iss(input);
string read_to_newline;
getline(iss, read_to_newline);
iss.str(input);
string read_to_tab;
getline(iss, read_to_tab, '\t');

cout << read_to_newline << "\n";
cout << read_to_tab << "\n";
}

In your case, the input is not a string within the program, it is the
user typing at the console. So replace the istringstream in my example
with cin.

Gavin Deane
 
S

Salt_Peter

MC said:
i work on TC++ (some old version). Please suggest something that works
in the same.

Please quote the message you are responding to.

This newsgroup is about C++, not some particular out-of-date compiler.
Any compiler that hopes to use C++ should at very least support the
<string> class.
Thats a bare minimum.
And since there are reasonably-compliant, free compilers out there,
i'ld suggest using one of them (ie: VC Express or g++). Many of these
come with capable IDEs as well.

You could write something like the following although that only works
because the const char* is static.

#include <iostream>
#include <ostream>

const char* const getstr()
{
static const char* const p_str = "a static string";
return p_str;
}

int main()
{
std::cout << getstr() << std::endl;
}

Passing arrays around is tricky and ugly. What you cannot do is
generate a temporary array and return a pointer to it. Thats begging
for disaster since functions have no state. So you'ld have to make the
array static (ewww). Arrays of chars are not equipped with a
terminator, something that a char* requires. So if you need an array of
10 chars:

#include <iostream>
#include <ostream>

const char* const str()
{
const size_t Size(10);
static char array[Size + 1]; // static !

char c = 'a';
for( size_t i = 0; i < Size; ++i )
{
array = c++;
}
array[Size + 1] = '\0'; // terminator
return array;
}

int main()
{
std::cout << str() << std::endl;
}

/*
abcdefghij
*/
 
D

David Pratt

Geo said:
Since I don't know what TC++ is, I don't know what works,. but if it
doesn't support the STL it isn't really C++ as I know it.



TC++ is Borlands Turbo C++, I am assuming, and yes it does support the STL
Strings library.
If you don't know how to work with C style strings, I suggest you read
a book, it's far to complicated to describe here.


However if You need to return a string value without using the string
library, you either need to return a pointer to a string that was allocated
on the heap with malloc; ie:

char * somefunc()
{
char * tmp = malloc(100);
tmp = "hello world\0";
return tmp;
};

or you need to pass the function a string by reference and return the
result in that.
void somefunc(char *tmp)
{
tmp = "Hello World!\0";
}

void main()
{
char[100] Str;
somefunc(&Str);
}
 
R

Rolf Magnus

Gavin said:
std::getline allows you to choose any delimiter character you want. The
default is newline but you can change that. This shows how it works.

#include <string>
#include <sstream>
#include <iostream>
using namespace std;

int main()
{
string input("abc\tdef\nghi");
istringstream iss(input);
string read_to_newline;
getline(iss, read_to_newline);
iss.str(input);
string read_to_tab;
getline(iss, read_to_tab, '\t');

cout << read_to_newline << "\n";
cout << read_to_tab << "\n";
}

In your case, the input is not a string within the program, it is the
user typing at the console. So replace the istringstream in my example
with cin.

However, the cin stream might be (and usually is) line buffered. In that
case, the getline call gives you everything up to the next tab character,
but the program will not receive the data until the user presses return or
the buffer is full.
In standard C++, there is no way to avoid that behavior.
 
R

Rolf Magnus

MC said:
i work on TC++ (some old version). Please suggest something that works
in the same.

I'd rather suggest to upgrade to a newer compiler that a standard library
implementation exists for. Without std::string (or another string classs)
you have to deal with all the complicated and obscure details of pointers,
arrays and dynamic memory handling just for doing some simple string
operations.
 
R

Rolf Magnus

David said:
However if You need to return a string value without using the string
library, you either need to return a pointer to a string that was
allocated on the heap with malloc; ie:

char * somefunc()
{
char * tmp = malloc(100);
tmp = "hello world\0";
return tmp;
};

Here you see what happens if you try to do C style string handling without
knowing every detail about memory handling, arrays and pointers. The above
function leaks memory. First, 100 bytes are allocated, and that memory
block's address is stored in tmp. In the next line, the pointer tmp gets
overwritten by the address of the string literal "hello world\0" (btw:
String literals already have a terminating \0 character. No need to
explicitly add a second one). Since there is no pointer anymore to the
dynamically allocated block of memory, that memory is lost forever. Now the
address of the string literal is returned. That part is ok, because string
literals have static storage duration. However, you returned a pointer to
non-const, and the literal is actually constant. An attempt to write to it
results in undefined behavior. Attempting to delete it, too.
What you should actually have done is use the strcpy function to copy the
string literal's content over to the dynamic memory (and document in red
uppercase letters that the user of the function is responsible for deleting
the memory).
or you need to pass the function a string by reference and return the
result in that.
void somefunc(char *tmp)
{
tmp = "Hello World!\0";
}

Well, this function is actually a no-op. tmp is a local pointer. You
overwrite this pointer, then the function returns. The local pointer is
destroyed, and nothing outside the function has changed. Again, you should
have used strcpy.
void main()

main() must return int.
{
char[100] Str;

That would have to be:

char Str[100];
somefunc(&Str);

And that:

somefunc(Str);

I'm sorry, but you must either have been drunk when you wrote that or you
shouldn't give advice about pointers and arrays in C++.
 
G

Geo

David said:
However if You need to return a string value without using the string
library, you either need to return a pointer to a string that was allocated
on the heap with malloc; ie:

char * somefunc()
{
char * tmp = malloc(100);
tmp = "hello world\0";
return tmp;
};

Oh no,no,no,no,no, how badly wrong can you go !!!!

I suggest you also need to read a book on memory handling.

Please refrain from giving any more 'advice' on the subject until you
do.
 
G

Gavin Deane

Rolf said:
However, the cin stream might be (and usually is) line buffered. In that
case, the getline call gives you everything up to the next tab character,
but the program will not receive the data until the user presses return or
the buffer is full.
In standard C++, there is no way to avoid that behavior.

Somehow I knew that testing the code with an istringstream (which was
easier because I could do it all programatically) was a shortcut that
wasn't quite valid. I should have thought it through properly (or just
tested it myself!). Thanks for pointing out the mistake.

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,054
Latest member
TrimKetoBoost

Latest Threads

Top