簡體   English   中英

如何將幾個不同的字符串分配給char *數組

[英]How to assign several different strings to a char* array

伙計們,我正在嘗試輸入以下幾個不同的字符串:

cap
to
cat
card
two
too
up
boat
boot

變成一個char *數組,如下所示:

char* result[9]

在使用for循環將所有這些字符串分配給數組后,我發現數組中的所有元素都是相同的,即“ boot”。

我的代碼和結果在這里:

#include<iostream>
#include<algorithm>
#include<cstring>
using namespace std;
int main()
{

    char* result[9];
    for(int counter=0;counter<9;counter++)
   {
        string temp;
        getline(cin,temp);
        result[counter]=(char*) temp.c_str();
        cout<<result[counter]<<endl;//correct
    }
cout<<endl;
cout<<endl;
for(int counter=0;counter<9;counter++)
    cout<<result[counter]<<endl;//false
}

這條線很好用,

 cout<<result[counter]<<endl;//correct

並打印所有不同的詞,例如:

cap
to
cat
card
two
too
up
boat
boot

但不知何故,這條線

 cout<<result[counter]<<endl;//false 

它只打印“啟動”九次。 我真的看不到這里的原因,希望你們能幫幫我,謝謝!

{
    string temp;
    getline(cin,temp);
    result[counter]=(char*) temp.c_str();   /* 1 */
    cout<<result[counter]<<endl;//correct
}  /* 2 */

在標記為1的行中,您將一個指向temp的基礎字符串數據的指針存儲在result[counter] 沒有字符串內容被復制; 您只是將現有數據的地址存儲在temp (順便說一下, .c_str()(char*)是什么.c_str()已經返回了一個指向char的指針。)

在標記為2的行中, temp被銷毀(這是該塊中的局部變量)。 現在, result[counter]包含無效的指針:指向的對象不再存在。

在此之后嘗試使用result的內容會result未定義的行為。

解決此問題的一種方法是使用字符串數組而不是指針數組:

string result[9];
for(int counter=0;counter<9;counter++)
{
    getline(cin,result[counter]);
    cout<<result[counter]<<'\n';
}

(我也刪除了endl因為不需要在每個字符串之后顯式刷新流。)

這也簡化了代碼,因為您不再需要temp變量:您只需將getline直接插入數組即可。

最好還是使用std::vector<string>

std::vector<std::string> result;
for(int counter=0;counter<9;counter++) {
  std::string temp;
  std::getline(std::cin, temp);
  result.push_back(temp);
}

如果要使用指針,則需要復制str.c_str()的內容,因為它是一個臨時變量,每次迭代后都會被銷毀。

您的代碼有問題,尤其是以下代碼行:

result[counter]=(char*) temp.c_str();

由於temp存在於for循環中,並且c_str()返回的地址一旦temp被破壞將是無效的,因此您的代碼將遭受UB的困擾。 該地址無效,因為c_str()

返回指向用作字符存儲的基礎數組的指針。

一旦temp超出范圍,該基礎數組就消失了,但是您現在可以在其范圍之外對其進行引用!

你應該為每個在字符串分配新的內存result也許使用strdup如下所示:

#include<iostream>
#include<algorithm>
#include<cstring>
using namespace std;
int main()
{

    char* result[9];
    for(int counter=0;counter<9;counter++)
   {
        string temp;
        getline(cin,temp);
        result[counter]=strdup(temp.c_str()); //now it is correct!
        cout<<result[counter]<<endl;
    }
cout<<endl;
cout<<endl;
for(int counter=0;counter<9;counter++)
    cout<<result[counter]<<endl;
}

不要忘記strdup將分配需要手動釋放的內存。

在以下循環中,您將聲明臨時字符串並一次又一次地使用它。 因此在循環的每次迭代中,都將編輯相同的指針。 因此,最后的值保持不變,其余值被覆蓋。

for(int counter=0;counter<9;counter++)
   {
        string temp;
        getline(cin,temp);
        result[counter]=(char*) temp.c_str();
        cout<<result[counter]<<endl;//correct
    }

相反,將您的臨時字符串聲明為容量為9的字符串數組。

#include<iostream>
#include<algorithm>
#include<cstring>
using namespace std;
int main()
{

    char* result[9];
        string temp[9];
    for(int counter=0;counter<9;counter++)
   {
        getline(cin,temp[counter]);
        result[counter]=(char*) temp[counter].c_str();
        cout<<result[counter]<<endl;//correct
    }
cout<<endl;
cout<<endl;
for(int counter=0;counter<9;counter++)
    cout<<result[counter]<<endl;//false
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM