转:一个strcpy的问题(很容易做错)
下面的执行结果是什么?
#include<stdio.h>
#include<string.h>
void main()
{
char s[]="";
char d[]="";
strcpy(d,s);
printf("d=%s,\ns=%s",d,s);
}
执行结果:d=56789,
s=123456789
书上有关于这个的解答,说是因为当初分配的内存地址是连续内存的问题,
原来的是1234\0123456789\0,strcpy后变成123456789\06789\0。
分析:首先要解释一下,char s[]="123456789"; char d[]="123"; 这样定义的数组和变量存放在栈内存中。
栈内存是一个自顶向下分布的数据结构,那么越先定义的变量地址就越高,越后定义的地址就越低。
s比d定义在前,那么s得到了高地址,而d得到了相对低的地址,那么内存中的存放形式就是
d[] <- | -> s[]
'1' '2' '3' '\0' | '1' '2' '3' '4' '5' '6' '7' '8' '9' '\0'
字符串拷贝后:
'1' '2' '3' '4 ' | '5' '6' '7' '8' '9' '\0' '7' '8' '9' '\0'
中间的‘|’表示s[]的起始位置。
所以此时输出的是s的值是 '5' '6' '7' '8' '9' '\0'。
这个题目出的很好,一方面考查了栈的生长方向,另一方面考查了strcpy的具体细节。
如果
char d[]="12",
char d[]="1" 答案是什么呢?
执行结果依旧是:d=56789,
s=123456789
字符串拷贝后:
这里就考虑对齐的问题,一般来说是4位一对齐。如果超过4位,就是8位一对齐。
char s[]="";
char d[]="";
printf("%p %p %p %p",d,d+,d+,d+); printf("\n%p \n",s); printf("%d\n",d[]);
运行输出:
0012FF38 0012FF39 0012FF3A 0012FF3B
0012FF3C
0 字符串结束符
Key看到d[3]是不存的。char d="12"占了4位。
如果
char d[]="1234",
char d[]="12345"
执行结果依旧是:d=9,
s=123456789
'1' '2' '3' '4 ' '5' '6' '7' '8' | '9' '\0' '7' '8' '9' '\0'
输出:
123456789
9
看另一程序.
#include<stdio.h>
#include<string.h>
void main()
{
char d[]="123";
char s[]="123456789";
strcpy(d,s);
printf("d=%s,\ns=%s",d,s);
}
虽然可以看到正确的输出结果d=123456789,s=123456789执,但是产生运行错误!!
这是因为字符串拷贝后,越过了目标字串的实际空间,访问到了不可预知的地址了。
参考:http://www.cnblogs.com/aquariusgx/archive/2011/02/16/1956320.html
转:一个strcpy的问题(很容易做错)的更多相关文章
- 自定义Jquery插件——由于项目需要,对页面中过长的文本进行截取,鼠标移上去有一个title的提示,所以做了一个Jquery过长文本处理的插件
由于项目需要,对页面中过长的文本进行截取,鼠标移上去有一个title的提示,所以做了一个Jquery过长文本处理的插件下面是代码: // 掉用方式支持 $('select').textBeauty(1 ...
- 一个老牌程序员说:做Java开发,怎么可以不会这 20 种类库和 API
- 转一个distinct用法,很有帮助
转一个distinct用法,很有帮助 (2011-12-01 15:18:11) 转载▼ 标签: 杂谈 分类: mysql复制 在使用mysql时,有时需要查询出某个字段不重复的记录,虽然mysql提 ...
- 不到50行代码实现一个能对请求并发数做限制的通用RequestDecorator
使用场景 在开发中,我们可能会遇到一些对异步请求数做并发量限制的场景,比如说微信小程序的request并发最多为5个,又或者我们需要做一些批量处理的工作,可是我们又不想同时对服务器发出太多请求(可能会 ...
- 【spring cloud】子模块module -->导入一个新的spring boot项目作为spring cloud的一个子模块微服务,怎么做/或者 每次导入一个新的spring boot项目,IDEA不识别子module,启动类无法启动/右下角没有蓝色图标
如题:导入一个新的spring boot项目作为spring cloud的一个子模块微服务,怎么做 或者说每次导入一个新的spring boot项目,IDEA不识别,启动类无法启动,怎么解决 下面分别 ...
- Git库搭建好之后,当要提交一个新的文件,需要做的是3个步骤
Git库搭建好之后,当要提交一个新的文件,需要做的是3个步骤 1.git add new.txt 2.git commit -m "add a new file" 3.git pu ...
- 大部分人都会做错的经典JS闭包面试题
由工作中演变而来的面试题 这是一个我工作当中的遇到的一个问题,似乎很有趣,就当做了一道题去面试,发现几乎没人能全部答对并说出原因,遂拿出来聊一聊吧. 先看题目代码: function fun(n,o) ...
- Bug2020011601,在ssh项目的applicaitonContext.xml中,少了一个双引号,打包成功(没报错),项目运行才发现
在ssh项目的applicaitonContext.xml中,少了一个双引号,打包成功(没报错),项目运行才发现. 加上少的双引号,解决了.
- 最近这两天看了关于H5游戏开发的一个教程,实践很短暂,看了很多理论的东西,现在呢也只是想回忆回忆关于EUI的部分知识吧
首先我了解了什么是Egret: Egret中文就是白鹭的意思,Egret是一套H5游戏开发的软件.(纯粹属于个人理解) 其次我对以下几款软件的相关知识做了些了解: Egret Engine(引擎),E ...
随机推荐
- return break continue 的区别
1)break 直接跳出当前的循环,从当前循环外面开始执行,忽略循环体中任何其他语句和循环条件测试.他只能跳出一层循环,如果你的循环是嵌套循环,那么你需要按照你嵌套的层次,逐步使用break来 ...
- html5的自定义data-*属性与jquery的data()方法的使用
人们总喜欢往HTML标签上添加自定义属性来存储和操作数据.但这样做的问题是,你不知道将来会不会有其它脚本把你的自定义属性给重置掉,此外,你这样做也会导致html语法上不符合Html规范,以及一些其它副 ...
- Hibernate之总结
以前做.net,最近做java项目,负责服务端的开发,直接用的jdbc,线程安全问题.缓存同步问题以及连接池什么的,都是手动写,不但麻烦而且容易出错.项目结束,赶快抽时间学了下hibernate,每天 ...
- html5test
html5test Github https://github.com/NielsLeenheer/html5test 主程序是 scripts/7/engine.js 目前看到的分类大部分是基于判断 ...
- css 清除浮动 兼容IE+, FF
上代码: <!doctype html> <html> <head> <meta charset="utf-8"> <titl ...
- javascript - 工作笔记 (事件绑定)
背景: 目前所做的项目,只能使用的是原生的javascript.对于javascript的事件绑定想必大家都懂得语法: 1,在标签中使用属性调用方法:<div onclick="AAA ...
- Qt信号槽机制的实现(面试的感悟,猜测每一个类保存的一个信号和槽的二维表,实际使用函数指针 元对象 还有类型安全的检查设定等等)
因为面试时问了我这道题,导致我想去了解信号槽到底是如何实现的,于是贴着顺序看了下源码,大致了解了整个框架.网上关于信号槽的文章也很多,但是大部分都是将如何应用的,这里我就写一下我所理解的如何实现吧, ...
- 字符串匹配——KMP算法
关于KMP算法的分析,我觉得这两篇博客写的不错: http://www.ruanyifeng.com/blog/2013/05/Knuth–Morris–Pratt_algorithm.html ht ...
- Mongodb数据库命令端经常使用操作
数据库基本命令操作 数据库经常使用命令 1.Help查看命令提示 help db.help(); db.yourColl.help(); db.youColl.find().help(); rs.he ...
- Loading Image
Android doesn’t handle animated gifs, but here’s one way to display an animated loading image that i ...