当前位置: 首页 > 知识库问答 >
问题:

当分配的字符数组溢出时,为什么我的C程序不会崩溃?

上官迪
2023-03-14

我有一个简单的C文件输入/输出程序,它演示了逐行读取文本文件,并将其内容输出到控制台:

/**
* simple C program demonstrating how
* to read an entire text file
*/

#include <stdio.h>
#include <stdlib.h>

#define FILENAME "ohai.txt"

int main(void)
{
    // open a file for reading
    FILE* fp = fopen(FILENAME, "r");

    // check for successful open
    if(fp == NULL)
    {
        printf("couldn't open %s\n", FILENAME);
        return 1;
    }

    // size of each line
    char output[256];

    // read from the file
    while(fgets(output, sizeof(output), fp) != NULL)
        printf("%s", output);

    // report the error if we didn't reach the end of file
    if(!feof(fp))
    {
        printf("Couldn't read entire file\n");
        fclose(fp);
        return 1;
    }

    // close the file
    fclose(fp);
    return 0;
   }

看起来我已经为每行256个字符(1024 <罢工> 字节数 即使我在第一行用超过1000个字符的文本填充ohai.txt,程序也不会分段错误,我假设它会这样做,因为它溢出了由输出[]数组指定的分配给它的可用空间量。

我的假设是,当操作系统有额外的可用内存时,它会为程序提供额外的内存。这意味着只有当ohai中的一行文本占用内存时,程序才会崩溃。txt导致堆栈溢出。

有更多C和内存管理经验的人可以支持或反驳我的假设,即为什么这个程序不会崩溃,即使文本文件的一行中的字符量远大于256?


共有3个答案

路金鑫
2023-03-14

fgets(输出, sizeof(输出), fp)在这种情况下读取(sizeof(输出)-1)字符数(否则它读取到换行符或文件末尾)

韩禄
2023-03-14

OP的程序没有崩溃,因为没有发生缓冲区溢出。

while(fgets(output, sizeof(output), fp) != NULL)
  printf("%s", output);

fgets()很好地读取一组char,最多为count或255或\n。然后printf("%s"...很好地将它们打印出来。这重复直到没有更多数据/

无崩溃、无溢出、无运行、无命中、无错误。

裴泰平
2023-03-14

这里没有溢出任何内容:fgets不会向缓冲区写入超过sizeof(输出)字符,因此不会溢出任何内容(请参阅留档)。

然而,如果确实使缓冲区溢出,则会出现未定义的行为。根据C规范,程序可能会执行任何操作:崩溃,而不是崩溃,无声地销毁重要数据,意外调用rm-rf等。因此,如果调用UB,不要期望程序崩溃。

 类似资料:
  • 我正在尝试更改下拉式适配器视图中的语言,该视图使用旋转adpater从字符串数组资源获取数据。我根据区域设置创建了两个不同的Strings.xml(一个用于法语,一个用于英语),但当我切换到法语并单击旋转器下拉菜单时,应用程序崩溃了。 下面是默认值目录中的Strings.xml 下面是values-fr-rFR目录中的strings.xml 这是自定义适配器中返回自定义视图的代码(视图是简单的文本

  • 问题内容: 当我退出“活动”退出(通过“后退”按钮)时,我的应用程序崩溃。据我所知,这是在Android代码库中发生的,而不是我的,但是我并不完全相信。 这是来自adb的stacktrace: 有人有什么想法/建议吗? 问题答案: 无助,因为没有代码。还在看 造成原因:android.app.Activity.performStop(Activity.java:3575)上的java.lang.N

  • 问题内容: 我的第一段代码是我的项目对象文件;第二个是主班。在运行代码没有任何问题之前,但是在添加读写文件之后,我的代码开始收到堆栈流错误。只是正在调用错误的代码段。 我的主班: 如何找到导致堆栈溢出的地方? 问题答案: 创建: 并创造 因此,在初始化时,您将不断创建这些对象 有一个类似的Baeldung示例,用于获取StackOverflowError 由于ClassOne的构造函数实例化了Cl

  • 问题内容: 我创建了一个简单的1文件Java应用程序,该应用程序循环遍历,调用某些函数,分配一些内存,添加一些数字等。我通过eclipse的运行该应用程序。 正在运行的应用程序显示在Java VisualVM下的。 我双击该应用程序,然后转到Profiler选项卡。 默认设置为: 我点击。的和按钮变灰。没发生什么事。 该说。 当我的应用终止时,says 。 我在这里做错了什么?我需要调整一些设置吗

  • 我将imageTextView编程为显示prenumeString的第一个字母,这是从编辑文本中获得的。问题是,每当编辑文本中出现所有字母时,应用程序就会崩溃。有什么想法吗? 代码: