首页
学习
活动
专区
工具
TVP
发布
精选内容/技术社群/优惠产品,尽在小程序
立即前往

将新成员函数添加到d指针类中断二进制兼容性?

在这个问题中,我们要讨论的是在C++中向一个类中添加新成员函数时,如何确保二进制兼容性。

在C++中,向一个类中添加新的成员函数时,如果该类已经被用于编译生成的二进制文件,那么新的成员函数可能会导致二进制兼容性问题。这是因为新的成员函数可能会改变类的内存布局,从而导致程序崩溃或其他不可预测的行为。

为了确保二进制兼容性,可以采用以下方法:

  1. 使用虚函数:将新成员函数声明为虚函数,这样可以确保在调用该函数时,程序会使用动态绑定来调用正确的实现。这种方法可以确保二进制兼容性,但可能会增加程序的运行时开销。
  2. 使用私有继承:如果新成员函数只在派生类中使用,可以将该函数声明为私有成员函数,并使用私有继承。这样可以确保新成员函数不会影响基类的内存布局,从而确保二进制兼容性。
  3. 使用Pimpl技术:Pimpl技术是一种将类的实现细节隐藏在一个指针中的技术。通过使用Pimpl技术,可以确保新成员函数不会影响类的公共接口,从而确保二进制兼容性。

总之,向一个类中添加新成员函数时,需要考虑二进制兼容性问题。可以使用虚函数、私有继承或Pimpl技术来确保二进制兼容性。

页面内容是否对你有帮助?
有帮助
没帮助

相关·内容

ABI 与 API 的区别

其中目标文件格式、符号修饰标准、变量内存分布方式、函数调用方式等这些跟二进制可执行代码兼容性相关的内容称为 ABI。...增加的内容有: (1)继承体系下的对象内存布局,比如基、虚基在继承中的位置; (2)指向成员函数指针(Pointer to Member)的内存分,如何通过指向成员函数指针调用成员函数,...如何传递this指针; (3)如何调用虚函数,虚函数表的内容和分布形式,虚函数指针在对象中的位置等; (4)template如何实例化; (5)外部符号的修饰; (6)全局对象的构造和析构;...C++ 新增的内容包括但限于以上内容,对 ABI 的兼容带了极大的挑战,C++ 二进制兼容性不够友好也一直为人诟病。...不仅不同编译器编译的二进制代码之间无法相互兼容,有时候连同一个编译器的不同版本之间的兼容性也不好。

1.7K20
  • pImpl

    函数:调用代码必须能够解析对成员函数的调用,包括无法访问的、由非私有函数重载的私有函数,如果私有函数更好地匹配,则调用代码无法编译。...这样打破了调用者对私有细节的依赖性,包括打破编译时依赖性和二进制依赖性 不需要为客户端代码定义仅在的实现中提到的类型,这可以消除多余的#include 并提高编译的速度 可以 更改的实现,即可以在impl...这是提供ABI-safety或二进制兼容性的有用技术,因此客户端代码不依赖于对象的确切布局。...但这样也会带来性能上 的损失: 每个construction/destruction必须allocate/deallocate memory 隐藏成员的每次访问都可能至少需要一次额外的间接访问(如果要访问的隐藏成员本身使用后向指针调用可见中的函数...如果虚函数覆盖了从基继承的虚函数,则它必须出现在实际的派生中 如果Pimpl中的函数需要依次使用可见函数,则它们可能需要指向可见对象的“后向指针”,这又增加了一个间接层次。

    88900

    《Effective C++》读书笔记(4):设计与声明

    你的type需要什么样的转换? 什么样的操作符和函数对此type而言是合理的? 什么样的标准函数应该驳回? 谁该取用type的成员?...当要返回的对象是一个局部栈对象时,函数退出后该对象就被销毁,无法通过指针或引用访问。因此函数返回值不能是指针或引用,必须是值传递。...return result; } Rational a,b,c,d; ... if((a*b)==(c*d)) //此时等号两边是同一个对象 正确的做法是:对于返回值而言,该用值传递是就用值传递...如果对于你的/模板来说,swap的默认实现的效率可接受,那么无需额外做什么;而如果默认实现的效率不足,通常源于为了二进制兼容性使用了pimpl技法,就需要实现一个确保不抛出异常的swap:...2、在/模板所在的命名空间提供一个non-member的swap,调用swap成员函数。 3、对于(而非模板),还需特化std::swap,调用swap成员函数

    19930

    【C++】与对象篇一

    C++是基于面向对象的,关注的是对象,一件事情拆分成不同的对象,靠对象之间的交互完 成 二 .的详解 1.的引入 C语言结构体中只能定义变量,在C++中,结构体内不仅可以定义变量,也可以定义函数...4.的作用域 定义了一个的作用域,在体外定义成员时,需要使用 :: 作用域操作符指明成员属于哪个域。...C++编译器给每个非静态的成员函数增加了一个隐藏的指针参数即this指针让该指针指向当前对象(函数运行时调用该函数的对象),在函数体中所有“成员变量”的操作,都是通过该指针去访问 1.this指针的特性...this指针的类型:类型 * const,即成员函数中,不能给this指针赋值 只能在成员函数的内部使用 this指针本质上是“成员函数”的形参,当对象调用成员函数时,将对象地址作为实参传递给 this...; d1.Print(&d1);//不隐藏,对象地址作为实参传递给 this形参 return 0; } this指针是“成员函数”第一个隐含的指针形参,一般情况由编译器通过ecx寄存器自动传 递,

    6210

    Google C++ 编程风格指南(二):作用域

    内联命名空间主要用来保持跨版本的 ABI 兼容性。 缺点: 名字空间具有迷惑性, 因为它们和一样提供了额外的 (可嵌套的) 命名轴线....优点: 某些情况下, 非成员函数和静态成员函数是非常有用的, 成员函数放在名字空间内可避免污染全局作用域....缺点: 成员函数和静态成员函数作为成员或许更有意义, 当它们需要访问外部资源或具有重要的依赖关系时更是如此. 结论: 有时, 把函数的定义同类的实例脱钩是有益的, 甚至是必要的....定义在同一编译单元的函数, 被其他编译单元直接调用可能会引入不必要的耦合和链接时依赖; 静态成员函数对此尤其敏感. 可以考虑提取到中, 或者函数置于独立库的名字空间内....注意只能用 raw 指针,别用智能指针,毕竟后者的析构函数涉及到上文指出的不定顺序问题。

    77630

    Visual C++ 中的重大更改

    根据标准,可变说明符仅可应用于数据成员的名称,不能应用于声明为 const 或 static 的名称,也不能应用于引用成员。...你无需为此使用枚举;具有 size_t 成员类型也起作用。 你还可以 placement new 全部消除作为备选解决方案。...U=D         ]           这是因为在第一次调用 is_base_of 时,尚未定义D”。...在这种情况下,解决方法是在定义之前,不使用此类类型特征。 如果 D 和 B 的定义移到代码文件的开头,错误将得到解决。...标准模板库          为了实现的优化和调试检查,C++ 标准库的 Visual Studio 实现特意破坏了连续两个版本之间的二进制兼容性

    4.8K00

    Visual C++ 中的重大更改

    根据标准,可变说明符仅可应用于数据成员的名称,不能应用于声明为 const 或 static 的名称,也不能应用于引用成员。...你无需为此使用枚举;具有 size_t 成员类型也起作用。 你还可以 placement new 全部消除作为备选解决方案。...U=D         ]           这是因为在第一次调用 is_base_of 时,尚未定义D”。...在这种情况下,解决方法是在定义之前,不使用此类类型特征。 如果 D 和 B 的定义移到代码文件的开头,错误将得到解决。...标准模板库          为了实现的优化和调试检查,C++ 标准库的 Visual Studio 实现特意破坏了连续两个版本之间的二进制兼容性

    5.2K10

    【云+社区年度征文】WinForm引用ActiveX组件,对Com组件的学习

    COM规范提供了支持跨平台软件重用的所有基本概念: 组件之间的函数调用的二进制标准。 功能强类型分组到接口中的规定。 提供多态性,功能发现和对象生存期跟踪的基本接口。...我们知道dll的接口是为了C设计的,它导出的基本都是C的函数,从原理上来说,dll加载到内存之后,会告诉你一组函数的地址,你自己call进去就可以调用相应的函数。...这里直接就出问题了,new方法通过编译器计算MyClass的大小来分配相应的内存空间,但是如果库升级了,相应的可能会增加成员,大小就变了,那么使用旧的定义分配出来的空间就不能在的库当中使用。...A应用通知COM Library,并输入接口的UUID,由COM Library装入B应用的该组件对应的dll,并把接口指针返回给A应用,指针里指示的是一堆函数指针,由这些指针,可以调用到B应用里的函数功能...这个程序集放到Dnspy反编译可以看到在ClsidAttribute标记有{ca8a9780-280d-11cf-a24d-444553540000},构造函数里面有UUID。

    1.9K40

    《C Primer》笔记(下篇)

    程序成功打开文件后,fopen()返回文件指针file pointer,其他I/O函数可以使用这个指针指向该文件。...传递结构的地址 可以结构体的地址传递给函数,当函数不能改变指针所指向值的内容时,需要把该结构体声明为一个指向const的指针。...o_data = n_data; // 把一个结构赋值给另一个结构 结构和结构指针的选择 选择把结构体指针作为参数有两个优点: 兼容性好,无论是以前还是现在的C都能实现这个方法 执行速度快,只需要传递一个地址...有一种较好的方法是每次使用malloc()为结构分配空间,同时也为指针分配空间(即我们需要另一个指针来跟踪分配的指针)。...: 项只能添加到链表的末尾 只能从链表的开头移除项 它本身是一种先进先出first in first out, FIFO的数据形式,下面我们给出非正式的抽象定义: 类型名: 队列 类型属性: 可以存储一系列项

    2.2K40

    Linux驱动开发-内核共享工作队列

    内核工作队列 工作队列常见的使用形式是配合中断使用,在中断的服务函数里无法调用会导致休眠的相关函数代码,有了工作队列机制以后,可以需要执行的逻辑代码放在工作队列里执行,只需要在中断服务函数里触发即可,...lockdep_map lockdep_map; #endif }; 在工作结构体里,只需要关心一个成员函数:work_func_t func; 这个成员函数是一个函数指针,指向工作函数指针;...*work); 功能 这是指向工作函数地址的函数指针,编写一个工作的函数。..._func:用来填充work_struct work结构的fun成员,就是工作函数指针。...static struct class *cls; //定义结构体指针 /*定义按键中断相关*/ static unsigned int irq_buff[4]; /*存放中断编号*/

    2.1K50

    C++教程(凯格尔训练法教程)

    18.3 文本文件的读写 18.4 二进制文件的读写 18.5 移动和获取文件读写指针 18.6 文本文件和二进制文件打开方式的区别 19 泛型和模板 19.1 函数模板 19.2 模板 19.3...(234,"yar") pp->show(); 指向对象成员指针 数据成员类型 *指针变量名 = &对象名.数据成员名; 函数类型 (名::*指针变量名)(参数列表); 指针变量名=&名::成员函数名...15.3 虚函数 实现程序多态性的一个重要手段,使用基对象指针访问派生对象的同名函数中的函数声明为虚函数,派生中的同名函数自动为虚函数。...二进制文件中,信息都占用 sizeof(对象名) 个字节;文本文件中成员数据所占用的字节数不同,占用空间一般比二进制的大。..."max" 实例参数类型为:(double, int) return 0; } 19.2 模板 声明了模板,就可以类型参数用于成员函数成员变量了。

    2.9K20

    嵌入式笔面试知识储备

    this指针 ​ this指针指向被调用的成员函数所属的对象。本质是一个指针常量,储存了调用他的对象的地址。...用途: 当形参和成员变量同名时,可用this指针来区分 在的非静态成员函数中返回对象本身,可使用return *this 特点: 只能在成员函数中使用,在全局函数、静态成员函数中都不能使用 this...this始终指向当前对象,静态成员函数属于。 this 指针是在成员函数的开始前构造,并在成员函数的结束后清除 。和函数的其他参数生命周期一样。...: ​ 如果是在函数体内动态申请内存的话,即便的线程调用这个函数也没事,因为的线程使用的是函数申请的动态内存(静态变量只有一份,所以多线程对于函数体内的静态变量改变会有无法修复的结果)。...相反,若进程数超过核数,进程分时使用CPU资源。 操作系统的功能 处理器管理:处理中断事件,进程管理。 存储器管理:内存管理。 设备管理:管理各类外围设备。

    70810

    C++教程(最全)「建议收藏」

    18.3 文本文件的读写 18.4 二进制文件的读写 18.5 移动和获取文件读写指针 18.6 文本文件和二进制文件打开方式的区别 19 泛型和模板 19.1 函数模板 19.2 模板 19.3...(234,"yar") pp->show(); 指向对象成员指针 数据成员类型 *指针变量名 = &对象名.数据成员名; 函数类型 (名::*指针变量名)(参数列表); 指针变量名=&名::成员函数名...15.3 虚函数 实现程序多态性的一个重要手段,使用基对象指针访问派生对象的同名函数中的函数声明为虚函数,派生中的同名函数自动为虚函数。...二进制文件中,信息都占用 sizeof(对象名) 个字节;文本文件中成员数据所占用的字节数不同,占用空间一般比二进制的大。..."max" 实例参数类型为:(double, int) return 0; } 19.2 模板 声明了模板,就可以类型参数用于成员函数成员变量了。

    2.5K30

    京东面经(含答案)

    都学过什么课程,计算机方向是软件工程吗 计算机网络,数据结构,操纵系统,编译原理,人工智能,大数据等随便你选几个,保证自己能说出个123 C++中的的大小计算 C++中成员函数,静态成员是不占的大小的...的大小等于基的大小+子类个non-static成员变量的大小再+非虚基大小,如果有多态性还要考虑vptr(可能不止一个)大小,这里成员变量是会被字节对齐的。...解决方案 1)我们1000瓶液体编号1~1000,然后编号转化为10位二进制,如1号就是0000000001; 2)十只小白鼠编号1~10; 3)液体的二进制编号上为1的位数给对应的小白鼠喝...智能指针内部实现(C++11) 智能指针一个计数器与指向的对象相关联,引用计数跟踪该类有多少个对象共享同一指针。...每次创建对象时,初始化指针并将引用计数置为1; 当对象作为另一对象的副本而创建时,拷贝构造函数拷贝指针并增加与之相应的引用计数;对一个对象进行赋值时,赋值操作符减少左操作数所指对象的引用计数(如果引用计数为减至

    86610

    【C++】继承 ⑥ ( 继承中的构造函数和析构函数 | 类型兼容性原则 | 父指针 指向 子类对象 | 使用 子类对象 为 父对象 进行初始化 )

    地方 , 都可以使用 " 公有继承 " 的 派生 ( 子类 ) 对象 替代 , 该 派生 ( 子类 ) 得到了 除 构造函数 和 析构函数 之外的 所有 成员变量 和 成员方法 ; 功能完整性 :..." 私有继承 " 的 派生 , 是 不具有 基 的 完整功能的 , 因为 最终继承 后的派生 , 无法在 外部调用 父的 公有成员 和 保护成员 ; 2、类型兼容性原则应用场景 " 类型兼容性原则...子类对象 , 父指针 值为 子类对象 在 堆内存 的地址 , 也就是 子类对象 地址 赋值给 父类型指针 ; 引用 : 父引用 引用 子类对象 , 子类对象 赋值给 父类型的引用 ; 二...// 子类对象 可以调用 父公有函数 child.funParent(); // 指向子类对象的指针传给接收父指针函数 // 也是可以的 fun_pointer...// 通过父指针调用父函数 p_parent->funParent(); // 指向子类对象的指针传给接收父指针函数 // 也是可以的 fun_pointer

    28420

    【C++】继承 ⑥ ( 类型兼容性原则 | 父指针 指向 子类对象 | 使用 子类对象 为 父对象 进行初始化 )

    地方 , 都可以使用 " 公有继承 " 的 派生 ( 子类 ) 对象 替代 , 该 派生 ( 子类 ) 得到了 除 构造函数 和 析构函数 之外的 所有 成员变量 和 成员方法 ; 功能完整性 :..." 私有继承 " 的 派生 , 是 不具有 基 的 完整功能的 , 因为 最终继承 后的派生 , 无法在 外部调用 父的 公有成员 和 保护成员 ; 2、类型兼容性原则应用场景 " 类型兼容性原则...子类对象 , 父指针 值为 子类对象 在 堆内存 的地址 , 也就是 子类对象 地址 赋值给 父类型指针 ; 引用 : 父引用 引用 子类对象 , 子类对象 赋值给 父类型的引用 ; 二...// 子类对象 可以调用 父公有函数 child.funParent(); // 指向子类对象的指针传给接收父指针函数 // 也是可以的 fun_pointer...// 通过父指针调用父函数 p_parent->funParent(); // 指向子类对象的指针传给接收父指针函数 // 也是可以的 fun_pointer

    30600

    分歧还是共存?详解Android内核安全

    sched: move no_new_privs into new atomic flags (sched: no_new_privs 移至的原子标志中),作者:Kees Cook 10.b6a12bf...为使内存访问有效,指针和内存标记必须匹配。HWASan依赖于ARMv8功能 Top-Byte-Ignore(TBI,也称为虚拟地址标记)指针标记存储在地址的最高位。...KASAN编译时内存函数插桩与影子内存相结合,以便跟踪运行时的内存访问,会有八分之一的内核内存空间专用于影子内存,以确定内存访问是否有效。目前在x86_64和 arm64架构中受支持。...在指针顶部字节中错误存储信息的Android应用一定会在启用了MTE的设备上中断。利用加标记的指针,可以在MTE设备可用之前更轻松地检测并拒绝对指针顶部字节的错误使用。...通过不兼容的函数指针间接调用函数导致CFI故障。当检测到CFI故障时,内核会输出一条警告,其中包括被调用的函数和导致故障的堆栈轨迹。可以通过确保函数指针始终与调用的函数属于同一型来修正此问题。

    1.5K30

    五年沉淀,微信全平台终端数据库WCDB迎来重大升级!

    成员指针并不指向一个具体的内存位置,它指向的是一个的特定成员,它的值跟这个成员的内存布局中的位置相关。...因为成员指针的类型是非常多样的,接收成员指针函数就必须写成模版,不同成员指针的组合使用的场景也就更加容易带来不同的模版实例化。...,但是在一个指定的范围内是唯一的,它可以作为关联数据表列名和成员变量的元信息的 key: 图3:成员指针作为key 有了这个映射关系之后,可以用成员指针来获取到列名,进而我们就可以用成员指针来表示数据表中的列...因为成员指针可以直接读写成员变量,一个直接的想法是使用成员指针来构造读写方法,然后读写方法的函数指针保存起来。...主要要解决两个问题,一个是如何在执行出错时获取到这个表格对应的 ORM ,一个是如何避免错误的列添加到表格中。

    1.1K21

    五年沉淀,微信全平台终端数据库WCDB迎来重大升级

    成员指针并不指向一个具体的内存位置,它指向的是一个的特定成员,它的值跟这个成员的内存布局中的位置相关。...因为成员指针的类型是非常多样的,接收成员指针函数就必须写成模版,不同成员指针的组合使用的场景也就更加容易带来不同的模版实例化。...,但是在一个指定的范围内是唯一的,它可以作为关联数据表列名和成员变量的元信息的 key: 图3:成员指针作为key 有了这个映射关系之后,可以用成员指针来获取到列名,进而我们就可以用成员指针来表示数据表中的列...因为成员指针可以直接读写成员变量,一个直接的想法是使用成员指针来构造读写方法,然后读写方法的函数指针保存起来。...主要要解决两个问题,一个是如何在执行出错时获取到这个表格对应的 ORM ,一个是如何避免错误的列添加到表格中。

    69541
    领券