能够访问索引大于数组长度的元素

时间:2012-06-12 07:47:06

标签: c++ arrays

以下代码似乎在运行时不应该运行。在这个例子中:

#include <iostream>
using namespace std;
int main()
{
    char data[1];
    cout<<"Enter data: ";
    cin>>data;
    cout<<data[2]<<endl;
}

输入长度大于1的字符串(例如,“Hello”)将产生输出,好像数组足够大以容纳它(例如,“l”)。当它试图存储一个比数组长的值或者它试图检索索引大于数组长度的值时,这不应该抛出错误吗?

3 个答案:

答案 0 :(得分:3)

  

以下代码似乎在不应该时运行。

关于“should”“should not”。它是关于“可能”“可能不是”

也就是说,您的程序可能会运行,也可能不运行。

这是因为您的程序调用了undefined behavior。访问数组长度之外的数组元素会调用未定义的行为,这意味着可能发生任何

编写代码的正确方法是使用std::string

#include <iostream>
#include <string>

//using namespace std;  DONT WRITE THIS HERE

int main()
{
    std::string data;
    std::cout<<"Enter data: ";

    std::cin>>data; //read the entire input string, no matter how long it is!

    std::cout<<data<<std::endl; //print the entire string

    if ( data.size() > 2 ) //check if data has atleast 3 characters
    {
         std::cout << data[2] << std::endl; //print 3rd character 
    }
}

答案 1 :(得分:1)

它可能在编译时在不同参数下崩溃或在其他机器上编译,因为运行该代码会根据文档给出未定义的结果。

答案 2 :(得分:1)

这样做是不安全的。它正在做的是写入恰好位于缓冲区之后的内存。然后,它会把它读回给你。

这只是起作用,因为你的cincout操作没有说:这是一个指向一个char的指针,我只会写一个char。相反它说:为我分配足够的空间来写。 cincout操作会一直读取数据,直到它们到达空终止符\0

要解决此问题,您可以将其替换为:

std::string data;

C ++会让你犯大错误。

一些可以节省大部分时间的“规则”:

1:使用char[]。而是使用string

2:不要使用指针传递或返回参数。通过引用传递,按值返回。

3:不要使用数组(例如int[])。使用vectors。你仍然需要检查你自己的界限。

只有这三个你将编写一些“安全”代码和非C代码。