[英]C++ pointer issues
我正在嘗試創建一個簡單的(模塊化)c ++程序,該程序讀取用戶輸入並將其吐出。
#include "stdafx.h"
#include <iostream>
#include <fstream>
#include <string>
using namespace std;
void _printOut(char * output)
{
cout << output << endl;
}
char * readUserInput()
{
char userInput[256];
cin >> userInput;
return userInput;
}
int _tmain(int argc, _TCHAR* argv[])
{
_printOut("Enter your name: ");
char * userName = readUserInput();
_printOut("Hello");
_printOut(userName);
system("pause");
return 0;
}
輸入您的姓名:aaaa您好╠╠╠╠╠╠╠╠按任意鍵繼續。 。 。
如果我在readUserInput函數中打印出userInput變量,它將打印出輸入的內容。 但是,嘗試在_tmain函數中將userInput變量存儲作為userName打印出來,會導致打印出一系列無法理解的字符。 即。 ╠╠╠╠╠╠╠╠。 據我的最佳猜測,這可能是由於指針問題引起的,但據我所知,我正確地引用了所有內容。
調試此代碼:在此行:_printOut(“ Hello”); 在此行的方法中:_tmain [userName =“ abcdefg”]:_printOut(userName); 在方法_tmain [userName =“†UX”]中
所以我想知道當用戶名的值在兩行之間未分配或操縱時如何變化。
char * readUserInput()
{
char userInput[256];
cin >> userInput;
return userInput;
}
char userInput[256];
數組僅在函數調用期間存在。 一旦您觸及了該函數的底部,它便不再存在,並且您將返回一個指向垃圾存儲區的指針。 這稱為本地范圍 。
而且無論如何,如果有人的名字真的很長(超過255
字符)。
考慮使用std::string
,它將解決兩個問題。
std::string readUserInput()
{
std::string inp;
std::cin >> inp;
return inp;
}
和
void printOut (const std::string& toPrint)
{
std::cout << toPrint << '\n';
}
(而且,這也不太重要,在這種情況下不允許使用_printOut
這個名稱,因為它以_
開頭。 請參見此處 ,盡管如果您是初學者,它可能會影響您的頭腦。)
編輯更好的方法是使用std::getline
一次將整行讀入std::string
。 但是,由於它們對待空格的方式,特別是'\\n'
換行符, getline(...)
和cin>>...
不能很好地配合使用。 通常最好在整個程序中選擇一個並堅持使用。 這是readUserInput()
外觀:
std::string readUserInput()
{
std::string line;
std::getline(std::cin, line);
return line;
}
這樣,如果用戶輸入包含空格的名稱(例如"BoB T. Fish"
),您將讀取整個名稱,而不僅僅是"BoB"
(然后剩下的內容在您下次閱讀時會引起您的困惑)。
將cin>>...
與getline
混合使用可能會很困難,原因是cin>>...
會讀到盡可能多的空白,然后將其余部分拋在后面。 因此,除了Mayb散布某人的姓氏之外,如果他們輸入的名字中沒有空格,它只會在輸入流中保留最后一個換行符。 然后,當您進行getline
,不會獲得用戶輸入的下一行。 您會得到留在后面的空行。 如果您再次使用cin>>
,則換行符將被忽略。 例如,考慮以下用戶輸入:
Hello\n
World\n
如果您首先使用cin>>
讀取,則會在程序中看到"Hello"
,並留下
\n
World\n
如果然后使用getline
進行第二次讀取,則會在程序中獲得""
,並留下
World\n
char userInput[256];
在readUserInput退出時將被銷毀,因此您返回的指針無效。
使用std::string
代替。
或動態分配變量,或將自動變量作為參數傳遞。
一旦超出范圍,userInput變量將被銷毀。
局部變量存儲在堆棧中。 函數執行完成后,變量將被銷毀。
您需要使用動態分配的char指針(存儲在堆上)或std :: string
您的問題是一個范圍界定問題:
char userInput[256];
定義一個局部變量,該局部變量僅在其自己的范圍內有效(在{}
括號之間)。
本質上,您將返回一個有效的指針,該指針在您離開該函數后將變為無效,因為它已被釋放。
您違反了一個基本規則:永遠不要返回指向局部(非靜態)變量的指針。
要解決此問題,請將您的userInput
靜態,或返回一個新字符串(使用new
每次調用都創建一個新字符串),或使用可復制對象而不是指針(例如std::string
)。
您正在使用指向緩沖區(在堆棧中)的指針,該緩沖區已超出范圍。
嘗試這個:
#include <iostream>
#include <fstream>
#include <string>
using namespace std;
void _printOut(char * output)
{
cout << output << endl;
}
char * readUserInput()
{
//Allocate in Heap, instead of stack
char* userInput = new char[256];
cin >> userInput;
return userInput;
}
int main(int argc, char* argv[])
{
_printOut("Enter your name: ");
char * userName = readUserInput();
_printOut("Hello");
_printOut(userName);
system("pause");
return 0;
}
更好的方法是使用std :: string
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.