当前位置: 首页 > news >正文

0813,引用,函数重载,内存布局叭叭叭


是我4句话5个ERROR,阿巴阿巴

001_arrpointer.cc

#include <iostream>
using std::cout;
using std::endl;void test(){int a[5]={1,2,3,4,5};int (*p)[5]=&a;cout<<p<<endl;cout<<p+1<<endl;int *pp=(int*)(&a+1);//第二个数组的首地址(*int)[5],强转成int*//变成第二个数组的首元素的地址cout<<*(a+1)<<"  "<<*(pp-1)<<endl;
}int main(void)
{test();return 0;
}

01,引用

reference.cc

#include <iostream>
using std::cout;
using std::endl;void test(){int num=100;int & ref=num;//& 不代表取值符,代表引用符号cout<<ref<<endl;ref=1000000;cout<<ref<<endl;int num2=200;ref=num2;//赋值int *p=&num;cout<<&num<<endl;cout<<&ref<<endl;//底层 cosnt poitercout<<&p<<endl;cout<<&num2<<endl;/* 特殊的常量指针,无法对其进行访问,只能间接访问到指向的对象/地址 */cout<<endl;const int & ref1=num;/* ref1=num2; *//* 不希望通过引用改变其本体,const */
}int main(void)
{test();return 0;
}

swap.cc

#include <iostream>
using std::cout;
using std::endl;void swap(int x,int y){
}void swap1(int *px,int *py){int z=*px;*px=*py;*py=z;
}//int & a=x,int & b=y
void swap2(int & a,int &b){int temp=a;a=b;b=temp;
}int num=100;
int func1(){return num; //执行return 语句的时候会发生copy
}
int & func2(){
//如果某个函数需要让其返回值是某个变量本身
//那么可以在函数返回类型中加上&return num; //no copy 
}
#if 0
int & func(){int num=1;return num;//num被销毁,悬空引用//确保引用绑定的本体的生命周期比函数更长
}
#endif
int & func4(){int *p=new int(10);return *p; //no delete
}void test(){int x=6,y=90;swap2(x,y);cout<<"x="<<x<<"  y="<<y<<endl;swap1(&x,&y);cout<<"x="<<x<<"  y="<<y<<endl;cout<<endl;cout<<&num<<endl;cout<<func1()<<endl; //临时变量cout<<func2()<<endl;  //绑定到num的引用cout<<&func2()<<endl;//对本体进行访问int & ref=func4();cout<<ref<<endl;delete &ref;//回收
}int main(void)
{test();return 0;
}

02,强制转换

typecast.cc           靓仔迷惑

#include <iostream>
#include <stdlib.h>
using std::cout;
using std::endl;void test(){int *p=(int*)malloc(sizeof(int));*p=100;free(p);p=nullptr;int *p1=static_cast<int*>(malloc(sizeof(int)));*p1=100;free(p1);p1=nullptr;cout<<endl;const int num=10;/* int a=const_cast<int>(num); *//* int a=const_cast<int>(10); *///把能const int -->intconst int *pp=&num;int *p2=const_cast<int*>(pp);//作用于 const引用和指向常量的指针*p2=100;cout<<*p2<<endl; //100cout<<num<<endl; //10cout<<p2<<endl;cout<<&num<<endl;}int main(void)
{test();return 0;
}

03,函数重载  04,默认参数

overload.cc

#include <iostream>
using std::cout;
using std::endl;//函数重载
//编译器的名字改变机制将函数的名字改编成了与参数信息相关的名字
int add(int x,int y){cout<<"int+int"<<" \t\t"; return x+y;}
int add(int x,int y,int z){cout<<"int+int+int"<<" \t\t"; return x+y+z;}
double add(double x,double y){cout<<"double+double"<<" \t\t"; return x+y;}
double add(int x,double y){cout<<"int+double"<<" \t\t"; return x+y;}
double add(double x,int y){cout<<"double+int"<<" \t\t"; return x+y;}
/* void  add(int x,double y){cout<<"int+double"<<" "; } *///用C的方式编译函数
//不可以进行函数重载
extern "C"{
int func(int x,int y){cout<<"int+int"<<" "; return x+y;}
/* int func(int x,int y,int z){cout<<"int+int+int"<<" "; return x+y+z;} */
int func01(int x,int y,int z){cout<<"int+int+int"<<" "; return x+y+z;}
}/* void ffunc(int x,int y){ */
/*     cout<<"x="<<x<<"\t\t"; */
/*     cout<<"y="<<y<<endl; */
/* } */
/* void ffunc(int x,int y=6){ */
/*     cout<<"x="<<x<<"\t\t"; */
/*     cout<<"y="<<y<<endl; */
/* }//备胎 */
void ffunc(int x=9090,int y=6){cout<<"x="<<x<<"\t\t";cout<<"y="<<y<<endl;
}//备胎/* void ff(int x=10086,int y); */
void ff(int x,int y=10086);
//实现与声明分离,建议默认值给声明
//顺序默认从右到左int dd(int x,int y,int z=100){cout<<"int+int+int"<<" \t\t"; return x+y+z;}
int dd(int x,int y){cout<<"int+int"<<" \t\t"; return x+y;}
//函数重载+默认值,可能会引发冲突void test(){cout<<add(1,2)<<endl;cout<<add(1,2,3)<<endl;cout<<add(1.5,2.5)<<endl;cout<<add(1,2.5)<<endl;cout<<add(1.3333,2)<<endl;cout<<add(1,2.77)<<endl;//缺省调用ffunc(10,9);ffunc(2);ffunc();ff(10,9);ff(10);cout<<dd(10,10,10)<<endl;/* dd(10,10); */
}void ff(int x,int y){cout<<"x="<<x<<"\t\t";cout<<"y="<<y<<endl;
}//备胎int main(void)
{test();return 0;
}

05,BOOL类型

bool.cc

#include <iostream>
using std::cout;
using std::endl;void test(){int x=true;int y=false;cout<<x<<endl;cout<<y<<endl;bool b1=1;bool b2=100;bool b3=0;bool b4=-1;cout<<b1<<endl;cout<<b2<<endl;cout<<b3<<endl;cout<<b4<<endl;// 1 1 0 1if(b4){cout<<"i love xixi"<<endl;}cout<<sizeof(b4)<<endl;
}int main(void)
{test();return 0;
}

06,INLINE函数

inline.cc   头文件需要声明和定义写一起

#include <iostream>
using std::cout;
using std::endl;//宏定义函数,不会检查,只替换
#define MAX(a,b) (a)>(b)?(a):(b)
#define MIN(a,b) {(a)>(b)?(a):(b)}//内联函数
//建议替换,(可能不采纳)
//更高级的替换,有安全检查机制
inline int max(int x,int y){return x>y?x:y; 
}void test(){/* cout<<MAX(20,10)+20<<endl; *//* cout<<MAX(10,20)+20<<endl; *//* cout<<MIN(20,10)+20<<endl; *//* cout<<MIN(10,20)+20<<endl; *///不是哥们,4句话 5个errorcout<<max(20,10)+20<<endl;cout<<max(10,20)+20<<endl;
}int main(void)
{test();return 0;
}

07,异常处理

catch.cc

#include <iostream>
using std::cout;
using std::endl;double division(double x,double y){if(y==0){throw "0 been division";}else if(x==0){throw 1.1;}return x/y;
}
void test(){try{double x=0,y=100;cout<<division(x,y)<<endl;cout<<"over"<<endl;}catch(const char*){/* cout<<msg<<endl; */cout<<" errr!!!!!"<<endl;}catch(double a){cout<<a<<endl;}cout<<"i love xixi"<<endl;
}int main(void)
{test();return 0;
}

08,内存布局

#include <iostream>
using std::cout;
using std::endl;const int xixi=90;
int gNum=1;
const int gcNum=20;void test(){int num=100;int num2=200;const int xixi1=100;cout<<&num<<endl;cout<<&num2<<endl;cout<<endl;cout<<&xixi<<endl;  //全局常量:文字常量区cout<<&xixi1<<endl; //局部常量 :staiccout<<endl;int *p=new int(20);int *p1=new int(30);cout<<p<<endl;cout<<p1<<endl;cout<<endl;cout<<&gNum<<endl;static int sNum=18;cout<<&sNum<<endl;cout<<endl;const char* pstr="i love xixi";cout<<pstr<<endl;printf("%p\n",pstr);//输出流运算符对char*的运算重载效果const int aaa=90909;/* int *const  pp=&aaa; */const int * pp=&aaa;cout<<pp<<endl;cout<<endl;cout<<static_cast<void*>(const_cast<char*>(pstr))<<endl;cout<<"&gcNum"<<&gcNum<<endl;cout<<endl;printf("%p\n",&test);
}int main(void)
{test();cout<<endl;printf("%p\n",&main);return 0;
}

09,C风格字符串

#include <iostream>
#include <cstring>
using std::cout;
using std::endl;void test(){char arr[3]={'i','s','\0'};char arr1[]={'a','q'};char arr2[]="i love xixi";cout<<arr<<endl;cout<<arr1<<endl;cout<<arr2<<endl;printf("%p\n",arr);printf("%p\n",arr1);printf("%p\n",arr2);
/* 0x7fff73681fd9 */
/* 0x7fff73681fd7 */
/* 0x7fff73681fdc */
//char * arr te shu xiao guo1const char* pp="i love xixi pp";/* char* pp="hello"; *//* pp[0]='H'; *///段错误cout<<pp<<endl;cout<<endl;const char* ps="i love xixxi ps";char* pssss=new char[strlen(ps)+1]();strcpy(pssss,ps);const char* pppp=new char[10]{'h','e','l','l','o'};cout<<pppp<<endl;cout<<pssss<<endl;delete [] pssss;pssss=nullptr;delete [] pppp;pppp=nullptr;}int main(void)
{test();return 0;
}

10,作业

01,在( )情况下适宜采用inline定义内联函数。(多选题)

  • A  函数体含有循环语句

  • B  函数体含有递归语句

  • C  函数代码少、频繁调用

  • D  函数代码多、不常调用

  • E  需要加快程序执行速度

02,写出下面程序的运行结果。   10/26  26/10  10/26  25/11

#include <iostream>using std::cout;
using std::endl;void f2(int &x, int &y)
{
int z = x;
x = y;
y = z;
}void f3(int *x, int *y)
{
int z = *x;
*x = *y;
*y = z;
}int main()
{
int x, y;
x = 10; y = 26;
cout << "x, y = " << x << ", " << y << endl;
f2(x, y);
cout << "x, y = " << x << ", " << y << endl;
f3(&x, &y);
cout << "x, y = " << x << ", " << y << endl;
x++; // ++x
y--;
f2(y, x);
cout << "x, y = " << x << ", " << y << endl;
return 0;
}

03,C++内存布局是怎样的?可以具体阐述一下么?

1,栈区
操作系统控制,高地址--》低地址(编译器优化显得低地址--》高地址)

2,堆区
程序员分配,低地址--》高地址,和栈区没有明确的界限

3,全局/静态区
读写段(数据段)存全局、静态变量

4,文字常量区
只读段,存程序中直接使用的文字常量和全局常量

5,程序代码区
只读段,存放函数体的二进制代码

04,在自定义命名空间MySpace中定义add函数,能够实现多个数据的加法(两个int、一个double一个int、一个int一个double、三个int),并跨模块调用add函数,使用using声明机制验证其功能。还可以适当给函数参数赋默认值,进行缺省调用的练习。

#include <iostream>
using std::cout;
using std::endl;//函数重载
//编译器的名字改变机制将函数的名字改编成了与参数信息相关的名字
int add(int x,int y){cout<<"int+int"<<" \t\t"; return x+y;}
int add(int x,int y,int z){cout<<"int+int+int"<<" \t\t"; return x+y+z;}
double add(double x,double y){cout<<"double+double"<<" \t\t"; return x+y;}
double add(int x,double y){cout<<"int+double"<<" \t\t"; return x+y;}
double add(double x,int y){cout<<"double+int"<<" \t\t"; return x+y;}
/* void  add(int x,double y){cout<<"int+double"<<" "; } *///用C的方式编译函数
//不可以进行函数重载
extern "C"{
int func(int x,int y){cout<<"int+int"<<" "; return x+y;}
/* int func(int x,int y,int z){cout<<"int+int+int"<<" "; return x+y+z;} */
int func01(int x,int y,int z){cout<<"int+int+int"<<" "; return x+y+z;}
}/* void ffunc(int x,int y){ */
/*     cout<<"x="<<x<<"\t\t"; */
/*     cout<<"y="<<y<<endl; */
/* } */
/* void ffunc(int x,int y=6){ */
/*     cout<<"x="<<x<<"\t\t"; */
/*     cout<<"y="<<y<<endl; */
/* }//备胎 */
void ffunc(int x=9090,int y=6){cout<<"x="<<x<<"\t\t";cout<<"y="<<y<<endl;
}//备胎/* void ff(int x=10086,int y); */
void ff(int x,int y=10086);
//实现与声明分离,建议默认值给声明
//顺序默认从右到左int dd(int x,int y,int z=100){cout<<"int+int+int"<<" \t\t"; return x+y+z;}
int dd(int x,int y){cout<<"int+int"<<" \t\t"; return x+y;}
//函数重载+默认值,可能会引发冲突/* void test(){ */
/*     cout<<add(1,2)<<endl; */
/*     cout<<add(1,2,3)<<endl; */
/*     cout<<add(1.5,2.5)<<endl; */
/*     cout<<add(1,2.5)<<endl; */
/*     cout<<add(1.3333,2)<<endl; */
/*     cout<<add(1,2.77)<<endl; *//*     //缺省调用 */
/*     ffunc(10,9); */
/*     ffunc(2); */
/*     ffunc(); *//*     ff(10,9); */
/*     ff(10); *//*     cout<<dd(10,10,10)<<endl; */
/*     /1* dd(10,10); *1/ */
/* } */void ff(int x,int y){cout<<"x="<<x<<"\t\t";cout<<"y="<<y<<endl;
}//备胎/* int main(void) */
/* { */
/*     test(); */
/*     return 0; */
/* } */
#include <iostream>
using std::cout;
using std::endl;extern int add(int,int);
extern double add(double,double);
void test0001(){cout<<add(2,5)<<endl;cout<<add(2.8989,5.789)<<endl;
}
int main(){test0001();return 0;
}

05,简述C++中引用与指针的联系与区别

联系:

1,都有地址的概念

2,引用的底层是靠指针实现的,可以视为一个受限制的指针

区别:

1,引用必须初始化,指针可以不初始化

2,引用不能修改绑定,指针可以

3,在代码层面,对引用本体取地址取到的是变量本体的地址,对指针取址取到的是指针变量的地址

06,什么是函数重载?其实现原理是什么?如何进行CC++的混合编程?

函数重载:C++允许函数名相同,参数类型、数量不同的函数在同一作用域同时出现

实现原理:名字改编(函数名称相同的时候,会根据参数的类型、顺序、个数进行改编,改变之后的函数名与函数信息相关

混合编程:extern "C" {}

07,什么是inline函数?inline与带参数的宏定义之间的区别是什么?

1,在函数最前面有inline关键字的声明函数
加上关键字,就是对编译器提出了内联的建议,如果建议通过,进行内联展开(即用用函数定义体 替代函数调用语句,该行为发生在编译阶段而非程序运行阶段

2,
宏函数: 优点(没有函数开销) 缺点(没有类型检查,安全隐患)
内联函数:不会增加开销,存在类型检查

08,引用作为函数返回值时要注意什么?如果函数返回值是绑定到堆上的变量的引用,应该如何安全地进行使用?

1,确保引用对象的生命周期比函数生命周期长

2,如果是堆上的内存,要避免内存泄漏(使用引用接收函数返回值,可以安全的访问堆上的变量,避免重复申请导致的内存泄露)

// 错误:返回局部变量的引用
int& getLocalValue() {int localValue = 10;return localValue;  // localValue 的生命周期结束后,引用变成悬空引用
}// 正确:返回堆上分配的对象的引用
int* getHeapValue() {int* heapValue = new int(10);return heapValue;  // 调用者负责释放内存
}int main() {int* value = getHeapValue();// 使用 valuedelete value;  // 释放内存return 0;
}

相关文章:

  • 北京网站建设多少钱?
  • 辽宁网页制作哪家好_网站建设
  • 高端品牌网站建设_汉中网站制作
  • C++的内存管理是怎样的?
  • 最小二乘法求拟合曲线(中线)的斜率和截距:数据背后的温柔对话
  • Python实例化指南之对象创建与初始化的实用技巧详解
  • 前端踩坑DOMException: Failed to execute ‘querySelector‘ on ‘Document‘: ‘#091.....‘
  • MySQL的InnoDB的页里面存了些什么 --InnoDB存储梳理(三)
  • .NET 8 跨平台高性能边缘采集网关
  • leetcode日记(72)最大矩形
  • 一文彻底搞懂Transformer - 总体架构
  • 后端开发学习路线
  • 蜂鸣器(51单片机)
  • 苹果微信不小心卸载了怎么恢复聊天记录?4招轻松解决
  • GPT-5:未来已来,你准备好了吗
  • Midjourney应用-用AI帮你做广告视频(动物走秀视频制作)
  • 第七节 流编辑器sed(stream editor)(7.2)
  • 三十六、【人工智能】【机器学习】【监督学习】- Bagging算法模型
  • 【挥舞JS】JS实现继承,封装一个extends方法
  • Asm.js的简单介绍
  • classpath对获取配置文件的影响
  • js作用域和this的理解
  • Meteor的表单提交:Form
  • Netty+SpringBoot+FastDFS+Html5实现聊天App(六)
  • Twitter赢在开放,三年创造奇迹
  • windows下mongoDB的环境配置
  • 使用putty远程连接linux
  • 通过来模仿稀土掘金个人页面的布局来学习使用CoordinatorLayout
  • 小而合理的前端理论:rscss和rsjs
  • 写给高年级小学生看的《Bash 指南》
  • 深度学习之轻量级神经网络在TWS蓝牙音频处理器上的部署
  • ​queue --- 一个同步的队列类​
  • # 移动硬盘误操作制作为启动盘数据恢复问题
  • #1014 : Trie树
  • #1015 : KMP算法
  • #QT(一种朴素的计算器实现方法)
  • (12)Linux 常见的三种进程状态
  • (14)Hive调优——合并小文件
  • (不用互三)AI绘画工具应该如何选择
  • (苍穹外卖)day03菜品管理
  • (读书笔记)Javascript高级程序设计---ECMAScript基础
  • (附源码)springboot 个人网页的网站 毕业设计031623
  • (南京观海微电子)——COF介绍
  • (四)stm32之通信协议
  • (一一四)第九章编程练习
  • (原創) 如何優化ThinkPad X61開機速度? (NB) (ThinkPad) (X61) (OS) (Windows)
  • (自适应手机端)响应式服装服饰外贸企业网站模板
  • .[backups@airmail.cc].faust勒索病毒的最新威胁:如何恢复您的数据?
  • .net core 6 使用注解自动注入实例,无需构造注入 autowrite4net
  • .net core 的缓存方案
  • .net 重复调用webservice_Java RMI 远程调用详解,优劣势说明
  • .NetCore 如何动态路由
  • .NET单元测试
  • .NET分布式缓存Memcached从入门到实战
  • .php文件都打不开,打不开php文件怎么办
  • .pyc文件是什么?
  • .vollhavhelp-V-XXXXXXXX勒索病毒的最新威胁:如何恢复您的数据?
  • @Autowired标签与 @Resource标签 的区别