c++:strcat潜在的错误不报告

不使用strcat函数,自己编程实现把两个字符串连接起来的程序(最终字符串长度限制在100个字符以内)。以下是部分代码,请完成并提交。 不使用strcat函数,自己编程实现把两个字符串连接起来的程序(最终字符串长度限制在100个字符以内)。以下是部分代码,请完成并提交。 #include <stdio.h> int main(){ char a[100],b[100]; int i,j; gets(a);//输入字符串a gets(b);//输入字符串b //下面代码把b连接到a的后面 … … puts(a);//输出... 阅读详情
#include<iostream>
#include<cstring>
using namespace std;
int main()
{
char a[]="hello";
char b[]="world";
cout<<strlen(a)<<endl;
strcat(a,b);
cout<<a<<endl;
cout<<strlen(a)<<endl;


}

运行结果:

5
helloworld
10

这个小程序中数组a的大小被改变了,但是可以正常运行。潜在的错误影响呢????


分析如下:http://blog.youkuaiyun.com/sendfeng/article/details/6215016。感谢sendfeng.

首先,这是一个非常有趣的问题!
我也是最近看了一本《C++高效编程:内存与性能优化》的书才弄明白其中的奥秘!
我们先来看一个“奇怪”的现象:

CODE:

        struct A { char a; long b; char c; long d; };
        struct B { char a; char c; long b; long d; };

        cout << sizeof(A) <<endl;
        cout << sizeof(B) <<endl;
按照常理,输出都应该是 10 ,其实实际运行结果是16,12 !是不是很奇怪???

为什么会出现这个现象呢?因为编译器会强制char类型的变量与long类型的变量在内存中对齐!


举例看结构A在内存中的布局如下:

地址   内 容
00     字符a
01     未用
02     未用
03     未用
04     long b, byte 0
05     long b, byte 1
06     long b, byte 2
07     long b, byte 3
08     字符c
09     未用
......
可以看到其中的原因了吧!

再看看LZ的程序的原因。
C++的系统函数strcat()的功能只是简单的拼接字符串,自身没有检测是否越界的功能!所以,当拼接后的新的字符串长度大于原始的空间时,strcat()会修改邻接的内存空间!所调用strlen()所取得的长度是截止到 '/0' 的长度!但是调用sizeof()会发现其空间大小还是10!
按照上面的说法,字符数组a后面的空间应该被修改,所以b的内容会变化,但是C++编译器分配内存空间是按照倒栈的顺序的,如果把b放到a前面定义,才有可能被修改!但是由于开始说的内存对齐问题的存在,因此字符数组b的内容还是没有被改变。


大家可以看看下面的程序,分别输出a,b的地址。

CODE:

int main(){

    char b[10] = "good";
    char a[10] = "java is";
    strcat(a," ");
    strcat(a,b);
    cout << int(&b) << endl;
    cout << int(&a) << endl;

    return 0;
}
运行结果为:

2293600
2293584


(该运行结果取决于不同的机器与编译器,但是反映的问题还是很明显的!)

a,b的头地址相距16Byte,而a的默认空间只有10Byte,还有6Byte的空间是什么呢?
当执行strcat()时,越界的部分就覆盖了这6Byte的内容,但是还没有影响到b的内容,为了证明strcat()确实存在越界的问题,我们可以构造一个特例,程序如下:

CODE:

int main(){

    char b[30] = "good, but i don't think so!";
    char a[10] = "Java is";
    strcat(a," ");
    strcat(a,b);
    cout<<a<<endl;
    cout<<b<<endl;
    cout << int(&b) << endl;
    cout << int(&a) << endl;

    return 0;
}
我们把b放得足够大,然后调用strcat(),使得拼接后的字符串的长度大于16,这样的话,不仅仅是a,b之间的6Byte被覆盖,b的内容也被覆盖了!
程序运行结果如下:

Java is good, but i don't think so!
t i'dont think so!

可以看到,越界是存在的!

最后总结一下:
strcat()存在越界的问题,因此我们在使用该函数之前需要确保目标字符数组的空间足够大!在原始的程序中,由于变量较少,运行似乎没错,但是还是有很严重的BUG的!


C++中strcat函数导致SIGSEGV段错误的原理与解决方案 在C++编程中,内存管理是核心基础概念,涉及指针操作、缓冲区分配和内存访问权限。其原理在于操作系统通过虚拟地址空间和内存保护机制管理进程内存,当程序试图越界访问或写入只读区域时,硬件会触发异常,操作系统则发送SIGSEGV信号终止进程,这就是段错误的本质。这一机制的技术价值在于保障系统稳定性和安全性,防止内存损坏导致更严重问题。应用场景广泛出现在字符串处理、网络数据包构建和文件路径拼接等需要动态内存操作的领域。本文聚焦于strcat函数引发的典型段错误,通过分析缓冲区溢出、只读内存写入等常见陷阱,结合str 阅读详情

相关推荐

标准库函数strcat 引起数组越界操作的分析与解决方法

前言 在使用字符串连接时,可能会想到:C标准库函数<string>中的:strcat strcat 需要注意目标字符串的长度,否则,不正确的使用,会引起数组的越界 测试例程 如下,执行:strcat_test时,发现了数组的越界,把其他内存的数据破坏了 void strcat_test(void) { uint32_t cnt = 0; char name0[8] = { 'a', '0' }; char name1[8] = { 'a', '

坚韧与专注 1533

strcat函数越界的问题

<br />首先,这是一个非常有趣的问题!<br />我也是最近看了一本《C++高效编程:内存与性能优化》的书才弄明白其中的奥秘!<br />我们先来看一个“奇怪”的现象:<br /><br />CODE:<br />        struct A { char a; long b; char c; long d; };<br />        struct B { char a; char c; long b; long d; };<br /><br />        cout << sizeof(

sendfeng的专栏 7108

Windows11安装Ubuntu 20.04.3 LTS双系统(详细过程)

一、基础环境 听说BIOS模式的传统MBR模式和新式UEFI模式,会对安装双系统产生影响。Windows11应该都是UEFI吧,可以按win+r输入msinfo32回车确认查看BIOS模式,我的电脑是UEFI+双硬盘 Ubuntu安装准备 1、 官网下载Ubuntu 20.04.3 LTS镜像iso文件:https://ubuntu.com/download/desktop 2、 下载官网推荐的U盘启动制作工具rufus: https://rufus.ie/ 3、制作启动u盘 插入U盘, 运行 rufu

学习随笔 9万+

那为啥书上说str1必须足够长?

今天遇到一个问题 strcat(str1,str2)中:如果str1不够长的话,会怎样?(是不是只会连接一部分str2的内容啊?) 答案是:如果str1不够长,那么该程序可能会出现bug 来直接看结果 可见,虽然给str1申请的长度小于str1+str2的长度,不过仍然是可以连接上的 尽管多运行几次,答案仍然是一样 这是可以运行,并且能拿到预期的结果,只不过程序有可能会出现bug 下面讲原理 此时我们给str1和str2申请的长度都是20,申请的空间是占用内存的,就大概是这样 strcat 函数复

qq_44769557的博客 1123

基于深度学习的UWB门禁检测

针对基于UWB技术智能门禁管理系统,由于测距误差或非视距原因导致门禁产生不合理动作的现象。分析如何采用基于深度学习的方法,通过对TWR测距数据、TWR监听数据、到达角度差(PDOA)、信道脉冲响应(CIR)等数据维度进行深度学习,利用 TensorFlow建立相应的推导模型,对卡片姿态进行更加精准可靠的检测,从而更好完成闸机开合控制。

tenth_quadrant的博客 2026

【故障排查】telnet连接失败:端口23不可达的深度分析与解决方案

本文深度剖析了telnet连接失败,特别是端口23不可达的常见原因与系统性解决方案。文章从客户端本地配置、服务器端服务与防火墙、中间网络路径三个层面,提供了详细的排查步骤与命令,并强调了Telnet协议的安全风险,建议使用SSH等更安全的替代方案进行远程管理与端口测试。

weixin_29306011的博客 895

小心使用strcpy函数时越界

strcpy()函数应该是我们用的比较常用的一个函数,基本功能是将一个字符串拷贝到我指定的内存空间。但是要复制的字符串长度超过这段内存空间的话,结果可能是未知的。 比如以下的程序: #include <stdio.h> #include <string.h> int main(int argc, char *argv[]) { int flag...

dichen3940的博客 855

【已解决,极简单!!】求助,R语言读取csv文件各种报错

【已解决】本来之前没问题,今天更新了Rstudioh以及R,就各种报错了。也看了目前能读取到的文件,从第一个中文字符直接就没有了。也就是说 还是读取中文字符的问题?新人初学,求大佬轻喷!

youyouluming945的博客 3876

C字符串操作strcat/strcat_s详解

前言 strcat、strcpy、strcmp、strlen是C中针对字符串的库函数,这四个函数不安全,然后C针对这个情况整出strcat_s、strcpy_s、strncmp、strnlen_s(这个并不是替代stelen的)来弥补。而在C++中一般用string。 这篇文章主要讲:strcat以及如何避免不安全的方法。 1 strcat 1.1 函数功能 把src所指字符串添加...

路漫漫其修远兮 4万+

第38节:cesium 风场效果(含源码+视频)

cesium 风场效果

qq_29384639的博客 2329

2、OTA/gm - C滤波器的架构与设计

本文深入探讨了OTA/gm-C滤波器的两种主要设计方法:基于LC梯形网络的设计与多环反馈(MLF)结构。前者包括元件替代法和信号模拟法,分别通过电感替代或电路方程模拟实现低敏感度滤波器;后者通过积分器级联与反馈网络合成全极点或含任意传输零点的传递函数。文中详细分析了不同结构如IFLF和LF的反馈矩阵、传递函数及性能差异,指出LF结构在敏感度、噪声和整体性能上的优势。同时比较了各类方法的优缺点及适用场景,为高频连续时间集成电路滤波器的设计提供了系统性指导。

fanta的博客 136

CPP strcat函数使用

strcat函数原型 char * strcat ( char * destination, const char * source ); strcat常见写法 // main.cpp // 字符数组strcat()函数的使用 // char * strcat ( char * destination, const char * source ); // 来源的头文件 #inc...

366

使用 WSL 在 Windows 上安装 Linux

开发人员可以在 Windows 计算机上同时访问 Windows 和 Linux 的强大功能。通过适用于 Linux 的 Windows 子系统 (WSL),开发人员可以安装 Linux 发行版(例如 Ubuntu、OpenSUSE、Kali、Debian、Arch Linux 等),并直接在 Windows 上使用 Linux 应用程序、实用程序和 Bash 命令行工具,不用进行任何修改,也无需承担传统虚拟机或双启动设置的费用。

隔壁老瓦的专栏 2872

【C++练习】27.在C++中连接字符串而不使用“strcat“函数

性能关键场景:在需要循环拼接大量字符串时,使用 “reserve()” 函数预先为 “std::string” 分配足够的空间,可以避免反复重新分配内存,从而大幅提升 “+=” 或 “append()” 的效率。直接对两个C风格字符串字面量(如 ““Hello” + “World””)使用 “+” 是错误的。需要注意的是,“stringstream” 的性能通常不如直接使用 “std::string” 的运算符或成员函数,因此更适用于调试、日志记录等对性能不敏感的格式化输出场景。

视睿 1336

国科大作业考试资料-人工智能原理与算法-2024新编-第十一次作业整理

1、有一位教授想知道学生是否睡眠充足。每天,教授观察学生在课堂 上是否睡觉,并观察他们是否有红眼。教授获得如下的领域知识: (1)没有观察数据时,学生睡眠充足的先验概率为0.7。 (2)给定学生前一天睡眠充足为条件,学生在晚上睡眠充足的概率是0.8;如果前一天睡眠不充足,则是0.3。 (3)如果学生睡眠充足,则红眼的概率是0.2,否则是0.7。 (4)如果学生睡眠充足,则在课堂上睡觉的概率是0.1,否则是0.3。 将这些信息形式化为一个动态贝叶斯网络,使教授可以使用这个网络从观察序列中进行滤波和预

MatsumotoChrikk 1055

蓝牙模块HM-10手册

蓝牙模块HM-10手册,该手册对蓝牙模块HM-10进行了详细的介绍和使用方法以及一些AT指令。

c语言strcat()/strcat_s()函数详解

前言 先看下strcat()/strcat_s()函数调用报错: 放大一点 严重性 代码 说明 项目 文件 行 禁止显示状态 错误 C4996 'strcat': This function or variable may be unsafe. Consider using strcat_s instead. To disable deprecation, use _CRT_SECURE_NO_WARNINGS. See online...

aoxuestudy的专栏 4365

迈瑞BS系列全自动生化分析仪LIS协议接口手册(内含HL7和ASTM)

迈瑞BS系列全自动生化分析仪LIS协议接口手册,内含HL7和ASTM)

【C++】字符串与字符数|组操作详解:strcpy 和 strcat 的使用与解析

C++ 作为一门强大的编程语言,为我们提供了丰富的字符串操作函数,这些函数多来自经典的 C 标准库。strcpy 和 strcat 是两个在字符串操作中非常常用的函数。初学者在学习这两个函数时,往往会面临概念模糊和潜在风险的问题。本篇文章将以深入浅出的方式讲解 strcpy 和 strcat 的用法,分析其原理与注意事项,同时结合代码示例与实际应用拓展,帮助读者全面掌握这两个函数。 2025.1.16-✍68min

禅宗里有一个词叫做“因缘和合”。 所谓因缘,是指事件要发生所必须的条件。因缘和合就是当你聚集了这件事的一切条件,它就会自然而然的发生。“它就会自然而然的发生”,这种朴素而坚定的价值观让我们感到无比安心,安心到可以不用有任何担心焦虑。 1241

VB摄像头监控

该VB模块可对摄像头捕获的画面进行录像等,可在创建的窗口进行控制

C# WinForm 基于DirectShow.dll编写的程序,可边预览边保存视频,音频和图片

基于微软的DirectShow.dll的二次开发1.自动识别连接的摄像头跟麦克风且可以对其进行选择(默认选中第一个)2.可录制wmv和avi两种格式的视频并且都带有音频,avi可以录制的分辨率和帧数进行选择,wmv默认进行了淸晰度优化如不喜欢可去除代码中有相关提示3.可在预览点开之后进行拍照,也可边录制视频边拍照4.添加了视频和音频的压缩功能(酌情使用)这次二次开发发现C#对DirectShow的相关信息太少,这次做完也不敢藏私共享出来,还望大家指正

c++ strcat函数越界

在使用strcat函数进行字符串连接时,编译通过,但显示却老错。 代码如下: #include "stdafx.h" #include<iostream> using namespace std; //char s1[]="uuuuuuuuuu"; int main() { char s1[] = "6"; char s2[] = "cvbb"; cout<&lt...

给你一拳 920

strcat 引发的思索

学过c的人,对这个strcat函数应该不会陌生吧, 其原型为extern char * strcat(char* str1,char* str2) 作用是连接str1和str2 ,并返回连接后的str1字符串。 在vs2005后,ms提供了更为安全的字符串连接:strcat_s; 为什么说strcat_s 更为安全那? 1、strcat 不会检测str1内存空间是否会越界 2、strc

小牛‘s Target 1599

strcat函数造成的段错误(Segmentation fault)

转自:http://book.51cto.com/art/201311/419441.htm 3.21 strcat函数造成的段错误 代码示例 intmain() { chardest[7]="12345"; char*src="abcdefghigklmnopqrstuvwxyz"; strcat(dest,sr...

weixin_33860147的博客 1911

C/C++混淆点-strcat和strcpy区别

一、原因分析 假设: char * str=NULL; str=new char[11];你想为字符串str开辟一个存储十个字符的内存空间,然后你现在有两个字符串:char * c1="abc"和char * c2="123";你想将这两个字符串都拼接在str字符串中,你想用strcat这个函数。但是你直接用strcat编译器会报错!!!不能这样做,应该在拼接之前使用memset(字符串...

weixin_38383877的博客 3524

C++笔记 strcat_s和strcat的区别

strcat_s在C/C++中,用于连接两个字符串的标准库函数,是strcat函数的增强版本。 需包含的预编译头文件 编辑 1、在C语言中:#include 2、在C++语言中:#include (可配合使用 using namespace std; 语句) 与 strcat 的区别 编辑 strcat_s是VS2005及以后新增的具有更强"

如果没有如果的博客 8928

C++题目--strcat函数

题目:请输出以下代码的结果? char d[20]="123"; char s[20]="abc"; strcat(d,s); int i=0; while(d[i++]!='\0') i++; printf("%d",i); 【参考答案】 结果为:7。 题目:为什么strcat(string,’!’);不行? 【参考答案】 字符和字符串的区别显而易见,而strcat()用于拼接...

用来学习的地方 936

C\C++中strcat()函数

将两个char类型链接。 char d[20]="GoldenGlobal"; char *s="View"; strcat(d,s); 结果放在d中 printf("%s",d); 输出 d 为 GoldenGlobalView (中间无空格) d和s所指内存区域不可以重叠且d必须有足够的空间来容纳s的字符串。 返回指向d的指针。 C函数

Zen 5530

编程技能:字符串函数06,strcat

编程技能:字符串函数

2401_82825368的博客 830

strcat运行报错,求助大佬

一运行就报错,把strcat那两行删了就能运行成功,求助。

ripple__ly的博客 479
上一篇: fortran+omp:必须在程序的开头声明OMP_GET_NUM_THREADS,OMP_GET_THREAD_NUM
下一篇: openmp 循环并行化---循环嵌套内部无法并行
crazyhacking
博客等级 码龄15年 299粉丝 148原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值