您的位置: 首页 - 站长

c 手机版网站开发网站安全检测软件

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

c 手机版网站开发,网站安全检测软件,书店网站策划书,做网站克隆一、引用 1、引用的概念 引用不是新定义一个变量#xff0c;而是给已存在变量取了一个别名#xff0c;编译器不会为引用变量开辟内存空 间#xff0c;它和它引用的变量共用同一块内存空间。 怎么说呢#xff0c;简单点理解就是你的小名#xff0c;家里人叫你小名#…一、引用 1、引用的概念 引用不是新定义一个变量而是给已存在变量取了一个别名编译器不会为引用变量开辟内存空 间它和它引用的变量共用同一块内存空间。 怎么说呢简单点理解就是你的小名家里人叫你小名你就不是你了显然不是这个就是引用的概念在变成过程中引用的用法就是如下方图片就是最简单的引用表示我先定义一个变量a然后给a取别名为b然后这里是把他们的地址都打印出来了然后发现他们的地址都是一个这样就能最简单的证明了引用就是取别名就是共同访问同一个地址。 那么能否给b接着取别名呢 当然可以了如果收别人叫你的小名再给这个小名去一个小名就不是自己了代码测试如图这样就可以得出引用是可以套用的。而这个就是引用的符号他和取地址符是同一个那是因为他的原理其实就是一个指针。 2、引用的特性 引用在定义时必须初始化因为引用和指针不同指针是存放这个变量的地址也就是说这个指针也可以不初始化放入空值都是可以的。 一个变量可以有多个引用这个就像上文中说的可以取好几个别名最间的的说明就是一个人是可以有很多称呼的如下图就可以看出对d取地址就可以看出也是a。 引用一旦引用一个实体再不能引用其他实体 这个引用不学指针可以更改地址引用是只可以对一个变量引用也就是说b是a的引用那么b只能是a的别名不可能存在b是别的别名那么就可以说明引用具有唯一性。 引用是具有等级权限的 最简单就是常量如下如图所示就可以看出如果对一个常量进行引用就会报错这就是引用的权限引用是只可以限制权限不能放大权限就像下图所示a是一个常量然后他的属性是只读那么b想引用他并且变成可以写的变量那肯定是不可以的但是假如说变量a是可以读写的引用的时候只限制成只读可以吗答案是可以的因为引用可以把权限变小如下图二所示是没有报错的就是可以的那么如何引用常量呢就是把权限限制为平级也就是也变成常量如下图三就是把别名也变成常量那么权限就是平级的了所以也就是可以使用引用了。 3、引用可以做什么 最简单的就是传参例如以前想要改变一个变量的值那么就需要传递一个指针过去但是有了引用就轻松多了可以直接传参过去然后函数内引用访问的还是这个变量的地址效果如图就是利用引用进行传参还有就是返回值就是经常使用的函授返回值例如ADD返回两数相加的和那么利用引用的话可以直接接收不会产生临时变量毕竟函数返回时在栈帧销毁时返回的值也是一个局部变量会在函数结束时随着栈帧的销毁而销毁所以函数的返回时本质是创建一个临时变量进行传参在销毁用引用传参如下图所示。 但是一般的函数是不能这样使用的因为如果一个函数在销毁后接着去访问这个地址可能会找到啥这个是不确定的因为临时变量是在会销毁的如果这个空间在销毁时没被随机值刷新那么可能会找到正确的值但是如果这个空间在销毁时被随机值刷新了 那么就是访问到随机值这个就是一个典型的越界访问了所以这样使用引用时是有限制的只有在静态变量、全局变量、栈帧还没没有销毁时、malloc等情况下才能用引用去取返回值其他的情况就需要使用返回值了那么对比一下引用和返回值的效率吧代码测试如下图可以看出差别还是挺大的。 #include time.h struct A { int a[10000]; }; void test1(A a) {} void test2(A a) {} void test3() {     A a;     size_t begin1 clock();     for (size_t i 0; i 100000; i)         test1(a);     size_t end1 clock();     size_t begin2 clock();     for (size_t i 0; i 100000; i)         test2(a);     size_t end2 clock();     cout end1 - begin1 endl;     cout end2 - begin2 endl; } int main() {     test3();     return 0; } 4、引用和指针的区别 在上面说过引用的原理其实就是指针但是引用和指针还是有点区别的区别如下 ① 引用概念上定义一个变量的别名指针存储一个变量地址。 ② 引用在定义时必须初始化指针没有要求 ③引用在初始化时引用一个实体后就不能再引用其他实体而指针可以在任何时候指向任何一个同类型实体 ④没有NULL引用但有NULL指针 ⑤在sizeof中含义不同引用结果为引用类型的大小但指针始终是地址空间所占字节个数(32位平台下占4个字节) ⑥引用自加即引用的实体增加1指针自加即指针向后偏移一个类型的大小 ⑦有多级指针但是没有多级引用 ⑧访问实体方式不同指针需要显式解引用引用编译器自己处理 ⑨引用比指针使用起来相对更安全  二、内联函数 以inline修饰的函数叫做内联函数编译时C编译器会在调用内联函数的地方展开没有函数调 用建立栈帧的开销内联函数提升程序运行的效率。 简而言之就是和宏的用处差不多宏是有缺陷因为在宏的使用时是直接替换的这样代码的安全性就大大下降了总结一下宏的优缺点 优点 1.增强代码的复用性。 2.提高性能。 缺点 1.不方便调试宏。因为预编译阶段进行了替换 2.导致代码可读性差可维护性差容易误用。 3.没有类型安全的检查 。 而内联函数的用法就是和宏差不多但是它可以把一个函数变成宏但是有一点就是内联时函数的代码是要求尽量简短当然如果过多时编译器依然会把他当成函数处理在简短 时内联函数就是直接替代从下图反汇编就可以看出内敛函数是直接替代的而不是call这个函数但是当行数过多时依然会当成函数调用了测试如下就可以看出内联函数也不是所有都可以替代。内联函数也不建议声明和定义分离分离会导致链接错误。因为内联函数被展开就没有函数地址了链接就会找不到 inline int ADD(int a, int b) {     return a b; } inline int ADD1(int a, int b, int c) {     c a b;     a a b;     b a b;     c a b;     a a b;     b a b;     c a b;     a a b;     b a b;     c a b;     a a b;     b a b;     c a b;     a a b;     b a b;     c a b;     a a b;     c a b;     b a b;     return c; } int main() {     int ret ADD(1, 3);     int ret1 ADD1(1, 3,2);     return 0; }