路遥见人心,日久知马力

博客园 首页 新随笔 联系 订阅 管理

指针的价值在于哪里?单纯为了迷惑别人?其实并非如此、本系列长期总结一些必须用指针或者用指针很好的场合:

写任何的代码都必须有一定的动机、而不是想怎么写就怎么写

写代码不是纯灵感的行为、也不是纯机械的行为、而是有逻辑的举一反三。

1. 把一个指针传入一个函数(签名里不加 const)的行为的动机:

  1) 减少拷贝的数据量-----函数的调用是用栈的(除非 inline 函数)、虽然可以简单认为拿函数体的代码替换掉函数调用一切都

  能正常工作、但编译器并不是这样干的、简单替换掉代码的语法是 宏、 宏和函数是不同的。

  2)期望函数内部的修改能反映到调用者

2. A 类保留一个 B类的指针的动机:

  1)如果保留的是 B 类的 一个对象、那么首先会占一块内存、如果是指针、那么就是占 4 或者 8 字节而已(取决于编译的平台)

  2)保留B类的对象、可以做到一种效果:

    B类的一个对象自己做了某些操作后,B类的状态改变了,但地址还是不变的,如果A之前拿到这个对象的地址,这时候A类拿这个地址就可以调这个对象的一些方法。

  3)可以在头文件里写个 class xxx * ,这样就暂时不需要引入实际的xxx的头文件、因为这个成员变量的大小是确定的。

3. 一个工厂函数、或者要做某些对象创建的函数、它们返回指针的动机:

  如果没有指针,像java一样、return new Person()? java的 new 语义也是产生一个指针(虽然看上去不是指针)

  而在C++ 如果 return 一个局部变量、其实也不是不行:

 

 

 但我在这种情况应该返回指针、而不是直接把变量返回了、因为这里是存在数据拷贝的、如果这个结构体不仅仅两个字段、而是10000个?那就恶心了

但返回指针能不能写成这样?这样最后的执行结果是什么?1 还是 2?还是别的?

 

 

 因为 p 是栈上的变量、但是第一次 genPoint()之后会弹栈、可是我们在main中还拿着人家的地址、并且希望x、y值不变

但假如又调用一次genPoint()、那么地址还是那个地址、但内容其实偷偷的就改了!!!

 

 

 所以说不是不能返回一个局部变量的地址、地址就是个整数、没有任何语法说返回整数都不行

但这样写程序是不符合我们的想法的、甚至假如我在genPoint()之后调用点别的东西、程序甚至会崩溃或者混乱、具体会发生什么可以去反汇编看看:

 

 

 总而言是、要从函数中返回”对象“(或者理解成结构体也行、c++里不挑这些毛病、对象就是一块内存、函数是不跟每个对象存在一起的!)

  1 可以返回栈上的变量、但这样有拷贝

  2.返回一个栈上的变量的地址、会有未定义的行为和高风险

  3.返回一个 new 出来的东西的地址、并且调用者要记得返回

  4.智能指针(暂时不讨论)

这样写智能指针还是错误的写法,只是简单的包装一层不会解决本质的问题、而且智能指针的初心是为了防止人们忘记释放内存

 

这样就对了:

 

 

 

 

 

 

posted on 2022-10-27 22:35  只讲大白话  阅读(73)  评论(0编辑  收藏  举报