0

我正在尝试创建一个strings (white space included)在用户输入之前应该输入的向量'!'

下面是我的代码:

#include <iostream>
#include <vector>
#include <string>
#include <iterator>

using namespace std;


int main()
{

   char buffer[100];
   string temp;
   vector <string> vec;


    while(1)//Shows Segmentation fault error while running,
    //compiles succesfully
    {
    cout << "Enter String : ";
    cin.get(buffer,100,'\n');//To ensure that whitespaces are also input
    cout << "@@@@ " << buffer << endl ;//Shows correct input

    cin.ignore(std::numeric_limits<std::streamsize>::max(),'\n');
    //Clearing cin stream for any residual characters
    temp.assign(buffer);//Assigning string the input "phrase"
    cout << "###" << temp << endl;//Shows correct output

    if (temp == "!") //if input is '!' character do not push on the vector a
    //come out of the loop
    break;

    vec.push_back(temp);//push on the vector
    temp.assign(NULL); //flush temp string

    }


  vector <string>::iterator p = vec.begin();
  //display thre vector
  while( p != vec.end())
   {
       cout << *p << endl;
       p++;
       }

    return 0;
    }

它编译成功,但在运行时抛出Segmentation fault错误。

无法弄清楚为什么?任何人都可以指出吗?

对此也有更聪明的解决方案,同时指出我的代码有什么问题。

谢谢

4

3 回答 3

3

这将是原因:

temp.assign(NULL);

asstd::string::assign()将尝试读取直到找到空终止符并且取消引用NULL指针是未定义的行为:在这种情况下是分段错误。在每次迭代中使用temp.clear()或只创建一个新对象。

使用std::getline()which 读取包含空格的行并避免对固定大小的数组进行硬编码(即buffer[100]):

std::string line;
while (std::getline(std::cin, line) && line != "!")
{
    vec.push_back(line);
}
于 2013-05-04T18:41:16.567 回答
3

尽管存在其他问题,但在(或可能任何其他调试器)中运行您的程序gdb揭示了原因:

tikal@seven ~$ g++ -o temp temp.cpp
tikal@seven ~$ gdb temp
GNU gdb 6.3.50-20050815 (Apple version gdb-1822) (Sun Aug  5 03:00:42 UTC 2012)
Copyright 2004 Free Software Foundation, Inc.
GDB is free software, covered by the GNU General Public License, and you are
welcome to change it and/or distribute copies of it under certain conditions.
Type "show copying" to see the conditions.
There is absolutely no warranty for GDB.  Type "show warranty" for details.
This GDB was configured as "x86_64-apple-darwin"...Reading symbols for shared libraries ... done

(gdb) run
Starting program: /Users/tikal/temp 
Reading symbols for shared libraries ++............................. done
Enter String : asd
@@@@ asd
###asd

Program received signal EXC_BAD_ACCESS, Could not access memory.
Reason: KERN_INVALID_ADDRESS at address: 0x0000000000000000
0x00007fff9081e6b0 in strlen ()
(gdb) backtrace
#0  0x00007fff9081e6b0 in strlen ()
#1  0x00007fff9857ab95 in std::string::assign ()
#2  0x0000000100001642 in main ()
(gdb) 

从本质上讲,temp.assign( NULL )这是一个坏主意。您可以temp.clear()改用,或者不打扰清除它(稍后您将重新分配它)。

于 2013-05-04T18:44:50.253 回答
1
while (getline(cin, temp) && temp != "!")
{
    vec.push_back(temp);
}

使用这样的缓冲区比 C++ 更像是 C 的事情。在 C++ 中,通常有一种方法可以避免使用类进行这种显式内存管理——这是一个很好的例子。

于 2013-05-04T18:41:19.857 回答