优雅绽放 發表於 2025-12-18 11:05:32

C语言gets()与fgets() 函数的区别

<div id="navCategory"><h5 class="catalogue">目录</h5><ul class="first_class_ul"><li>1.gets() 函数</li><li>2.fgets() 函数(推荐使用)</li><li>3. 重要区别对比</li><li>4.fgets() 的换行符问题</li><li>5. 实际使用示例</li><ul class="second_class_ul"><li>5.1 安全输入示例:</li><li>5.2 处理长输入:</li></ul></ul></div><p><strong>使用要点:</strong></p>
<ol><li><strong>永远不要使用 gets()</strong></li><li><strong>总是使用 fgets()</strong> 替代 gets()</li><li><strong>记得处理换行符</strong></li><li><strong>检查返回值</strong>确保读取成功</li><li><strong>考虑输入缓冲区清理</strong></li></ol>
<p class="maodian"></p><h2>1.gets() 函数</h2>
<p><strong>基本用法:</strong></p>
<div class="jb51code"><pre class="brush:cpp;">char *gets(char *str);
</pre></div>
<ul><li>从标准输入读取一行字符串</li><li>遇到换行符或文件结束符停止</li><li><strong>不检查数组边界</strong>,存在安全隐患</li></ul>
<p><strong>示例:</strong></p>
<div class="jb51code"><pre class="brush:cpp;">#include &lt;stdio.h&gt;

int main() {
    char name;
    printf("请输入姓名:");
    gets(name);// 危险!可能发生缓冲区溢出
    printf("你好,%s!\n", name);
    return 0;
}
</pre></div>
<p>⚠️ <strong>gets() 的问题</strong>:</p>
<ul><li><strong>缓冲区溢出风险</strong>:如果输入超过数组大小,会导致内存破坏</li><li><strong>C11标准已弃用</strong>,C17标准中<strong>完全移除</strong></li><li>现代编译器会给出警告</li></ul>
<p class="maodian"></p><h2>2.fgets() 函数(推荐使用)</h2>
<p><strong>基本用法:</strong></p>
<div class="jb51code"><pre class="brush:cpp;">char *fgets(char *str, int n, FILE *stream);
</pre></div>
<ul><li><code>str</code>:存储字符串的缓冲区</li><li><code>n</code>:最大读取字符数(包括结尾的<code>\0</code>)</li><li><code>stream</code>:输入流(stdin 表示标准输入)</li></ul>
<p><strong>示例:</strong></p>
<div class="jb51code"><pre class="brush:cpp;">#include &lt;stdio.h&gt;

int main() {
    char name;
   
    printf("请输入姓名:");
    fgets(name, sizeof(name), stdin);// 安全!
    printf("你好,%s!\n", name);
   
    return 0;
}
</pre></div>
<p class="maodian"></p><h2>3. 重要区别对比</h2>
<table><thead><tr><th>特性</th><th>gets()</th><th>fgets()</th></tr></thead><tbody><tr><td><strong>安全性</strong></td><td>不安全,已弃用</td><td>安全,推荐使用</td></tr><tr><td><strong>边界检查</strong></td><td>无</td><td>有,指定最大长度</td></tr><tr><td><strong>换行符处理</strong></td><td>丢弃换行符</td><td>保留换行符在字符串中</td></tr><tr><td><strong>返回值</strong></td><td>成功返回str,失败返回NULL</td><td>成功返回str,失败返回NULL</td></tr></tbody></table>
<p class="maodian"></p><h2>4.fgets() 的换行符问题</h2>
<p><code>fgets()</code> 会保留换行符,需要手动处理:</p>
<div class="jb51code"><pre class="brush:cpp;">#include &lt;stdio.h&gt;
#include &lt;string.h&gt;

int main() {
    char input;
   
    printf("输入字符串:");
    fgets(input, sizeof(input), stdin);
   
    printf("处理前的字符串:%s\n",input);
    printf("===========\n");
   
    // 去除换行符
    size_t len = strlen(input);
    if (len &gt; 0 &amp;&amp; input == '\n') {
      input = '\0';
    }
   
    printf("处理后的字符串:'%s'\n", input);
    return 0;
}
</pre></div>
<p>执行效果:</p>
<blockquote><p>输入字符串:abcd efgh ijklmn<br />处理前的字符串:abcd efgh ijklmn &nbsp;</p>
<p>===========<br />处理后的字符串:&#39;abcd efgh ijklmn&#39;</p></blockquote>
<p>(可以看到,处理前的字符串自带有换行符。)</p>
<p class="maodian"></p><h2>5. 实际使用示例</h2>
<p class="maodian"></p><h3>5.1 安全输入示例:</h3>
<div class="jb51code"><pre class="brush:cpp;">#include &lt;stdio.h&gt;
#include &lt;string.h&gt;

void safe_input() {
    char buffer;
   
    printf("请输入文本(最多%d字符):", sizeof(buffer)-1);
   
    if (fgets(buffer, sizeof(buffer), stdin) != NULL) {
      // 去除换行符
      buffer = '\0';
      
      printf("你输入的是:%s\n", buffer);
      printf("字符串长度:%zu\n", strlen(buffer));
    } else {
      printf("读取失败!\n");
    }
}

int main() {
    safe_input();
    return 0;
}
</pre></div>
<p>执行效果:</p>
<blockquote><p>请输入文本(最多49字符):hello,world!<br />你输入的是:hello,world!<br />字符串长度:12</p></blockquote>
<p class="maodian"></p><h3>5.2 处理长输入:</h3>
<div class="jb51code"><pre class="brush:cpp;">#include &lt;stdio.h&gt;

void clear_input_buffer() {
    int c;
    while ((c = getchar()) != '\n' &amp;&amp; c != EOF);
}

int main() {
    char line;
   
    printf("输入字符串:");
    fgets(line, sizeof(line), stdin);
   
    // 检查是否读取了完整行
    if (line != '\n') {
      printf("警告:输入被截断!\n");
      clear_input_buffer();// 清空输入缓冲区
    }
   
    printf("结果:%s\n", line);
    return 0;
}
</pre></div>
<blockquote><p>输入字符串:hello, hello, hello, world!!!<br />警告:输入被截断!<br />结果:hello, he</p></blockquote>
<p>到此这篇关于C语言gets()与fgets() 函数的区别的文章就介绍到这了,更多相关C语言gets()与fgets() 内容请搜索琼殿技术社区以前的文章或继续浏览下面的相关文章希望大家以后多多支持琼殿技术社区!</p>
                           
                            <div class="art_xg">
                              <b>您可能感兴趣的文章:</b><ul><li>C语言入门学习之fgets()函数和fputs()函数</li><li>C语言中输入函数(scanf()、fgets()和gets())的区别详解</li><li>详解C语言gets()函数与它的替代者fgets()函数</li></ul>
                            </div>

                        </div>
                        <!--endmain-->
頁: [1]
查看完整版本: C语言gets()与fgets() 函数的区别