2011-05-08 13 views
0

ちょっと、私は次のようなstring_to_80char()関数を使用しているため、優先する文字列クラスで作業するためにpdCursesのaddstr()を取得しようとしています(Windows curses)これは唯一のパラメータであるため、文字列を受け取り、80文字の長さの文字配列 (コンソールの1行に1文字の文字数が入る)を返す。pdcURSESとaddstrとの文字列の互換性の問題

しかし、次のコードを実行すると「@」または「4」のようなランダムな文字が印刷された「ちょうど文字列」を取得します。

問題は何ですか?助けてくれてありがとう! =)

#include <curses.h>   /* ncurses.h includes stdio.h */ 
#include <string> 
#include <vector> 
#include <Windows.h> 
#include <iostream> 
using namespace std; 

char* string_to_80char (const string& aString) 
{ 
    int stringSize = aString.size(); 
    char charArray[90]; 

    if(stringSize <= 80) 
    { 
    for(int I = 0; I< stringSize; I++) 
     charArray[I] = aString[I]; 
    for(int I = stringSize; I < sizeof(charArray); I++) 
     charArray [I] = ' '; 
    return charArray; 
    } 

    else 
    { 
    char error[] = {"STRING TOO LONG"}; 
    return error; 
    } 
}; 


int main() 
{ 
    // A bunch of Curses API set up: 
    WINDOW *wnd; 

wnd = initscr(); // curses call to initialize window and curses mode 
cbreak(); // curses call to set no waiting for Enter key 
noecho(); // curses call to set no echoing 

std::string mesg[]= {"Just a string"};  /* message to be appeared on the screen */ 
int row,col;    /* to store the number of rows and * 
        * the number of colums of the screen */ 
getmaxyx(stdscr,row,col);  /* get the number of rows and columns */ 
clear(); // curses call to clear screen, send cursor to position (0,0) 

string test = string_to_80char(mesg[0]); 
char* test2 = string_to_80char(mesg[0]); 
int test3 = test.size(); 
int test4 = test.length(); 
int test5 = sizeof(test2); 
int test6 = sizeof(test); 

addstr(string_to_80char(mesg[0])); 
refresh(); 
getch(); 


cout << endl << "Try resizing your window(if possible) and then run this program again"; 
    system("PAUSE"); 
refresh(); 
    system("PAUSE"); 

endwin(); 
return 0; 
} 

答えて

2

あなたstring_to_80char()は、ローカル変数へのポインタを返す関数がそうポインタがごみを指して戻るとき、その変数の寿命が終わりました。また、返された文字列の末尾に'\0'文字を入れないでください(ただし、返す文字列は正式には存在しません)。

は、発信者が(未テストの例)に80 char文字列を入れるためのバッファを提供しておいてください。

また
char* string_to_80char (const string& aString, char* buf, size_t bufSize) 
{ 
    int stringSize = aString.size(); 
    enum { 
     max_buf_size = 81; /* 80 plus the '\0' terminator */ 
    }; 

    bufSize = (bufSize < max_buf_size) ? bufSize : max_buf_size; 

    if (stringSize+1 < bufSize) { 
     return NULL; /* or however you want to handle the error */ 
    } 

    /* we know the buffer is large enough, so strcpy() is safe */ 
    strcpy(buf, aString.c_str()); 

    return buf; 
}; 

、呼び出し側が解放する必要があり、その場合には、ヒープ上で返されるバッファを割り当て、(それを返します彼らがそれを完了したときにバッファリングします)。

char* string_to_80char (const string& aString) 
{ 
    int stringSize = aString.size(); 

    if(stringSize <= 80) 
    { 
     return strdup(aString.c_str()); 
    } 

    return strdup("STRING TOO LONG"); 
}; 

あなたがWindows上だとstrdup()を持っていない場合は、ここであなたが行く:

#include <stdlib.h> 
#include <string.h> 
#include <assert.h> 

/* 
* public domain strdup() 
*/ 

char* strdup(char const* s) 
{ 
    size_t siz = 0; 
    char* result = NULL; 
    assert(s); 

    siz = strlen(s) + 1; 
    result = (char*) malloc(siz); 

    if (result) { 
     memcpy(result, s, siz); 
    } 

    return result; 
} 
0

一つの問題は、(あなたがstring_to_80charにスタックに保存されている変数へのポインタを返すことです)。この変数はスタック上に保存されます。

char charArray[90]; 

あなたは、その関数から戻ると、この変数によって使用されるストレージは、もはや有効ではなく、再利用するために、その可能性が高いです。 addstr()のスタック変数がこの同じストレージを上書きして、文字列が壊れている可能性があります。

簡単な修正は、それがスタックに割り当てられていないので、charArrayの静的を作ることです。

static char charArray[90]; 
0
addstr(mesg[0].c_str()) 

はあなたが必要とするすべてである必要があります。 PDCursesはCライブラリなので、Cの文字列が必要です。彼らは80列または何か特別なものである必要はありません。

int my_addstr(const string &aString) 
{ 
    return addstr(aString.c_str()); 
} 

また、簡単なC++ラッパー関数を作ります