c++值传递和引用及指针传递区别
以下程序各有何问题?
***********************************************************************************************************************************
1.
void getmemory(char*p)
{
p=(char *) malloc(100);
}
int main()
{
char *str=NULL;
getmemory(str);
strcpy(str,“helloworld”);
printf("%s\n",str);
}
首先先回顾值传递与指针传递,引用传递的区别:
#include <iostream.h>
void swap(int x,int y)
{
int temp;
temp=x;
x=y;
y=temp;
}
void swap(int *x,int *y)
{
int temp;
temp=*x;
*x=*y;
*y=temp;
}
void swap(int& x,int& y)
{
int temp ;
temp=x;
x=y;
y=temp;
}
void main()
{
int x=5; int y=6;
swap(x,y);
*****5,6;值传递是在函数作用域中建立变量或对象的副本,一旦函数结束副本消失,不影响原值;
/*swap(&x,&y);*/
******6,5;指针传递传递的是变量或对象的地址,是在对变量或对象的原值进行操作,会改变原值;
/*swap(x,y);*/
*******6,5;引用传递形式如值传递但效果同指针传递,是原来变量或对象的别名,是在对变量或对象的原值进行操作
cout<<“交换后:x=”<<x;
cout<<“y=”<<y<<endl;
}
题1就如同是值传递,对原值str不起任何影响,str 依旧是NULL,每运行一次就有一块内存泄露,所以当函数的参数是一个指针,不要指望用该指针去申请动态内存。
*********************************************************************************************************************************
2.
void getmemory(char*p)
{
p=(char *) malloc(100);
strcpy(p,“helloworld”);
}
int main( )
{
char *str=NULL;
getmemory(str);
printf(“%s/n”,str);
free(str);
return 0;
}
有题1 可知道,str最终没有分配到内存,free(str)是危险操作;
************************************************************************************************************************************
3.
void *getmemory(void)
{
char p[]="hello";
return p;
}
int main()
{
char *str=NULL;
str=getmemory();
printf("%s\n",str);
}
不要用return 语句返回指向“栈内存”的指针,因为该内存在函数结束时自动释放,str指向的地址原先内容不可知,现有内容不清楚,输出乱码
注意:函数的返回值是指针类型的,检查是静态内存指针还是堆内存指针还是栈内存指针,栈内存指针是绝对要不得滴
************************************************************************************************************************************
4.
void getmemory(char** p,int num)
{
*p=(char*)malloc(num);
}
int main()
{
char *str=NULL;
getmemory(&str,100);
strcpy(str,“helloworld”);
printf("%s\n",str);
}
用指向指针的指针(二级指针)申请动态内存,(c中常用的指针传递)该函数能正常输出helloworld,但是忘记free()会造成内存泄露;
注意:(指针传递,一级指针)函数中只能对指针的指向的值(*p)进行修改,
而不能修改指针地址(改变p值,*p不变)!
例:
void fun(int *p)
{
int b=100;
p=&b; // b的地址并没有被返回
}
程序4:
void fun(int *p)
{
*p=100; // okay
}
(函数要求修改指针参数的地址,必须使用指针的指针!(二级指针)
(那么c++中可以运用引用传递来动态申请内存void getmemory(char*& p,int num))
********************************************************************************************************************************
5.
int main()
{
char* str=(char*)malloc(100);
strcpy(str,“hello”);
free(str);
if(str!=NULL)
{
strcpy(str,“world”);
printf(str);
}
return 1;
}
str 所指的内存被释放,但是str 所指的地址仍然不变,if(str!=NULL)没有任何作用。
str变成野指针,“野指针”不是NULL 指针,是指向“垃圾”内存的指针,
“野指针”的成因主要有两种:
(1)指针变量没有被初始化。任何指针变量刚被创建时不会自动成为NULL 指针,它
的缺省值是随机的,它会乱指一气。所以,指针变量在创建的同时应当被初始化,要么
将指针设置为NULL,要么让它指向合法的内存。例如
char *p = NULL;
char *str = (char *) malloc(100);
(2)指针p 被free 或者delete 之后,没有置为NULL,让人误以为p 是个合法的指针。
(3)指针操作超越了变量的作用范围。这种情况让人防不胜防,示例程序如下:
class A
{
public:
void Func(void){ cout << “Func of class A” << endl; }
};
void Test(void)
{
A *p;
{
A a;
p = &a; // 注意 a 的生命期
}
p->Func(); // p 是“野指针”
}
函数 Test 在执行语句p->Func()时,对象a 已经消失,而p 是指向a 的,所以p 就成了“野指针”。
*********************************************************************************************************************************
内存管理:
中软面试题:
内存有哪几种存储组织结构.请分别加以说明《来自高质量c/c++编程》
1.从静态存储区域分配:
内存在程序编译时就已经分配,这块内存在程序整个运行过程都存在。(全局变量,static变量)
2.在栈上创建:
函数内部的局部变量在栈上创建,函数结束后,这些存储单元会自动释放。 分配内存效率高,但是分配内存容量有限。
3.从堆上分配(动态内存分配):
由malloc()和new()手动分配内存,由delete(),free()手动释放内存空间。内存空间由程序员自己决定,可分配的内存容量大。
注意:
malloc申请的是连续的一块内存,当返回NULL表示内存申请失败,用if(NULL!=p)验证, 若是内存分配失败用exit(1),终止整个程序; 栈出现内存泄露情况通常是由没有回收垃圾资源,没有进行内存释放引起的
free(p);斩断了指针与这块内存的关系,
虽然指针P仍然保存原来的地址,但是已经失去了对那块内存的控制权,同样,对应的那块内存虽然内容存在,不过,已经无法利用其中的数据,成为垃圾文件。对于每次malloc()只能有一次free(),若free()两次会出错,除非原指针指向NULL
全局变量和局部变量有什么区别?是怎么实现的?操作系统和编译器是怎么知道的?
生命周期不同:全局变量随主程序创建和创建,随主程序销毁而销毁;局部变量在局部函数内部,甚至局部循环体等内部存在,退出就不存在;内存中分配在全局数据区。
使用方式不同:通过声明后全局变量程序的各个部分都可以用到;局部变量只能在局部使用;分配在栈区。
操作系统和编译器通过内存分配的位置来知道的,
全局变量分配在全局数据段并且在程序开始运行的时候被加载。局部变量则分配在堆栈里面。
fmoonstar 更新至2011.11.4
转载于:https://www.cnblogs.com/phpzhou/p/6390860.html
c++值传递和引用及指针传递区别相关推荐
- c++引用与指针的区别
★ 相同点: 1. 都是地址的概念: 指针指向一块内存,它的内容是所指内存的地址:引用是某块内存的别名. ★ 区别: 1. 指针是一个实体,而引用仅是个别名: 2. 引用使用时无需解引用(*),指针需 ...
- 引用和指针的区别?传引用比传指针安全,为什么?如果我使用常量指针难道不行吗?
引用和指针的区别 (1) 引用在创建的同时必须初始化,即引用到一个有效的对象:而指针在定义的时候不必初始化,可以在定义后面的任何地方重新赋值. (2) 不存在NULL引用,引用必须与合法的存储单元关联 ...
- C++中引用与指针的区别(详细介绍)
转载:http://www.cnblogs.com/tracylee/archive/2012/12/04/2801519.html C++中的引用与指针的区别 指向不同类型的指针的区别在于指针类型可 ...
- 引用和指针的区别[zz]
(1)引用总是指向一个对象,没有所谓的 null reference .所有当有可能指向一个对象也由可能不指向对象则必须使用 指针. 由于C++ 要求 reference 总是指向一个对象所以 ref ...
- 2-5:C++快速入门之引用,引用和指针的区别
文章目录 (1)引用的概念 (2)引用的特点 (3)常引用 (4)引用的应用场景 A:做参数 B:做返回值 (5)引用和指针 在第一次学习C语言指针时,许多教材上都会给出一个交换两个变量值的例子,开始 ...
- C++ 引用详解(引用的特点,引用与指针的区别,引用的其他使用)
目录 引用 一.引入 二.C++中较为麻烦的运算符 三.引用的定义 四.引用的特点 五.对比指针与引用 六.引用与指针的区别(重点) 1.语法层面的区别 2.汇编层面的区别 七.引用的其他使用 引用 ...
- 浅谈C++中引用和指针的区别
之前我们介绍了什么是引用,错过的小伙伴们可以戳这里 ↓ https://blog.csdn.net/Sun_Life_/article/details/89304920 既然引用底层是用指针形式实现的 ...
- C++中的引用与指针的区别
C++中的引用与指针的区别 指向不同类型的指针的区别在于指针类型可以知道编译器解释某个特定地址(指针指向的地址)中的内存内容及大小,而void*指针则只表示一个内存地址,编译器不能通过该指针所指向对象 ...
- 【C语言】引用和指针的区别?
首先解释在C语言中,什么是引用: 1.引用概念 引用是别名,必须在声明的时候初始化.即:是指一个已定义变量的别名.(一个内存空间,有两个名字都可以操作) 引用:在函数调用时,是变量的别名,不可以单独 ...
- C++ 引用以及引用与指针的区别
概述 前面整理了指针的用法,但是经常和指针拿来对比东西是引用.确实指针在使用的过程中会有很多的麻烦,比如赋初值.使用时判空.无效指针.深浅拷贝等等.在我看来引用的指针的高级替代,它的使用规则规避了很多 ...
最新文章
- UPC2710T高频放大器
- gitlab-ci详细说明
- 利用js实现 禁用浏览器后退| 去除上一个历史记录链接
- JavaScript数据结构和算法 1
- AUTOSAR从入门到精通100讲(十二)-V2X通信安全技术要求标准
- Spark_UDAF
- 外星人bios按f2调风扇_外星人电脑上海维修站地址「上海市飞雕国际大厦2703室」...
- java lambda map用法_Java 中如何使用 lambda 表达式填充 Map?
- 随想录(被高估的busybox)
- 牛客寒假算法基础训练营6
- 相机靶面大小和显微镜FN的匹配关系
- 医疗数据分析——过高费用的异常检测
- 互联网版本(支持手机APP)云天售后服务软件上线
- 广州搬砖第三年,从一枚小菜鸡到架构师
- 牛顿法 泰勒二次展开式
- 如何查找涉密文件_涉密文件信息资料保密管理规定
- 开始学习python了鸭
- 数字IC设计入门(3)初识电路图
- 10种招聘数据的采集方法
- leetcode 494. 目标和
热门文章
- 悲剧!IDEA 突然找不到类了?
- PHP html 转换成PDF wkhtmltopdf HTML 转换成 PDF (JAVA C#都适用)
- js原生继承几种方式
- 阶段1 语言基础+高级_1-3-Java语言高级_09-基础加强_第3节 注解_18_注解_案例_简单的测试框架...
- 收获,不止oracle
- IOS VFL语言(页面布局)
- 转发 JBPM工作流小结
- (转)C# 解析 json
- [原]解决百度地图多个Marker和InfoWindow时总是打开最后一个InfoWindow的问题
- SSIS常用的包—通用的属性