Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
893 views
in Technique[技术] by (71.8m points)

c++ - Returning char* from function not working

Visual studio c++ shows that "string" on line 24 has one array element, but the top contains all the text that was input by the user. But when I send to PutString(), it disappears. Why?

#include <stdio.h>

void PutString( const char* pChar ){
    for( ; *pChar != 0; pChar++ )
    {
        putchar( *pChar );
    }
}

char* GetString(){
    char c[100];
    int i = 0;
    do
    {
        c[i] = getchar();
    }while( c[i++] != '
' );
    c[i] = '';
    // PutString( c );
    return c;
}

void main(){
    char* string = GetString();
    PutString( string );
}
See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

Because c is a local variable within GetString and you are returning its address, after which it disappears (moves out of scope). That's undefined behaviour - you're not allowed to use stuff that's gone out of scope. In fact, if you run that through gcc, it tells you that quite explicitly:

qq.cpp:9: warning: address of local variable ‘c’ returned

If you want to return non-simple things (such as arrays instead of integers or floats, which make a copy for you) from a function, you need to (for example) dynamically allocate it so that it survives function return. Something like changing:

char c[100];

into:

char *c = malloc (100); // or equivalent 'new'.

(and remembering to free/delete it eventually, of course).

Even though you may see it in the debugger when you return from GetString, it's still not guaranteed as per the standards.

In any case, there's a good chance the next stack manipulation (such as calling PutString) will wipe out the information.


Here's a C++ version that does it the new/delete way:

#include <stdio.h>

void PutString (const char* pChar ){
    for (; *pChar != 0; pChar++)
        putchar( *pChar );
}

char* GetString (void) {
    char *c = new char[100];      // memory behind c will survive ...
    int i = 0;
    do {
        c[i] = getchar();
    } while (c[i++] != '
');
    c[i] = '';
    return c;
}                                 // ... past here ...

int main (void) {
    char* string = GetString();
    PutString (string);
    delete[] string;              // ... until here.
    return 0;
}

I should also mention that there are probably better way to get line-based input in both C (fgets or see an earlier answer of mine) and C++ (such as the string getline and the char array getline).


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...