C++该函数隐藏

本文深入探讨了C++中虚拟函数的使用及其隐藏机制,通过实例展示了如何在派生类中覆盖基类函数,以及如何通过指针区分基类与派生类的行为。详细解释了函数覆盖与隐藏的区别,并提供了代码示例进行说明。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >


只有基类成员函数的定义已声明virtualkeyword,当在派生类中的时间,以支付功能实现,virtualkeyword可以从时间被添加以增加。它不影响多状态。

easy混淆视听,掩盖:
,规则例如以下:

1) 假设派生类的函数与基类的函数同名,可是參数不同。

此时,不论有无virtualkeyword,基类的函数将被隐藏(注意别与重载混淆)。

2) 假设派生类的函数与基类的函数同名。而且參数也同样,可是基类函数没有virtualkeyword。

此时,基类的函数被隐藏(注意这样的情况与函数重载的差别,重载发生在同一个类中。

)。


#include<iostream>
using namespace std;

class Base
{
public: 
	virtual void f(float x)
	{
		cout<<"BASE::f"<<x;
	}
	virtual void g(float x)
	{
		cout<<"BASE::g"<<x;
	}
	void h(float x)
	{
		cout<<"BASE::h"<<x;
	}
};
class Driver:public Base
{
public: 
	void f(float x)
	{
		cout<<"d::f"<<x;
	}
	virtual void g(int x)
	{
		cout<<"d::g"<<x;
	}
	void h(float x)
	{

		cout<<"d::h"<<x;
	}
};

int main(int argc, char const *argv[])
{
	Driver d;
	Base* pb=&d;
	Driver* pd=&d;
	pd->f(1.2f);
	pb->f(1.2f);
	pd->g(1.2f);
	pb->g(1.2f);
	pd->h(1.2f);
	pb->h(1.2f);
	return 0;

}

请大家注意,f()函数属于覆盖,而g()与h()属于隐藏。从上面的运行结果,我们能够注意到在覆盖中。用基类指针和派生类指针调用函数f()时。系统都是运行的派生类函数f(),而非基类的f()。而在隐藏方式中,用基类指针和派生类指针调用函数g()、h()时,系统会进行区分,基类指针调用时,系统运行基类的g()、h(),而派生类指针调用时,系统“隐藏”了基类的f(),运行派生类f(),这是“藏”起源。

版权声明:本文博主原创文章,博客,未经同意不得转载。

<think>嗯,用户问的是C++中的函数隐藏概念及其作用机制。我需要先回顾一下相关的知识点,确保自己理解正确。首先,函数隐藏和重载、重写容易混淆,得先区分清楚这三个概念。根据引用[3],C++支持函数重载,而函数重写涉及到虚函数,这在引用[1]和[2]里有提到。函数隐藏可能是在派生类中定义同名函数导致基类函数隐藏的情况。 接下来,我需要明确函数隐藏的定义。根据已有的知识,当派生类中的函数与基类的函数同名,但参数列表不同,且基类函数没有被声明为虚函数时,派生类函数隐藏基类的同名函数。这种情况下,无论参数是否相同,基类函数在派生类作用域中不可见。这和函数重载不同,重载发生在同一作用域,而隐藏涉及不同作用域。 然后,作用机制方面,隐藏的发生条件需要详细说明。比如,派生类中的函数是否必须有不同的参数?如果参数相同但基类函数非虚,会发生隐藏吗?这时候应该属于重写的情况,但如果基类函数不是虚函数,那么实际上会隐藏而不是重写,导致多态性无法实现。这可能是一个容易出错的地方,需要特别指出。 另外,用户可能想知道如何避免意外的函数隐藏。比如,使用using声明将基类函数引入派生类作用域,这样就可以保留基类的函数,避免被隐藏。这部分需要举例说明,让用户更清楚如何操作。 还要考虑用户可能的疑问,比如隐藏和重载的区别,以及隐藏与重写的区别。引用[3]提到了函数重载和隐藏的不同,应该结合例子来说明。例如,基类有一个函数void func(int),派生类定义void func(double),这时候基类的func(int)会被隐藏,即使参数不同,只要同名就会隐藏,这和重载需要同一作用域不同。 最后,总结函数隐藏的应用场景和注意事项,比如在需要屏蔽基类某些方法时使用,但要注意可能导致的意料之外的行为。同时,强调正确使用虚函数来实现多态,避免误用隐藏导致的问题。 需要确保回答结构清晰,分点解释,并给出代码示例帮助理解。可能还需要检查引用是否正确,引用[3]主要讨论函数隐藏,所以需要正确引用。同时,用户的问题只涉及函数隐藏,但可能需要简要对比重载和重写,以帮助区分概念。 现在,整理思路,分步骤回答:定义、发生条件、作用机制、与重载重写的区别、如何避免、示例代码、应用场景。确保每个部分都有明确的说明,并引用相关文献支持。</think>### C++函数隐藏概念及作用机制 #### 一、定义与核心特点 函数隐藏(Function Hiding)是C++中当**派生类定义了与基类同名的函数**时,基类同名函数在派生类作用域中不可见的现象。此现象与函数是否虚函数无关,核心在于**作用域覆盖**和**名称查找规则**[^3]。 #### 二、发生条件 1. **同名函数**:派生类定义了与基类完全同名的函数(包括重载版本)。 2. **作用域规则**:基类函数未通过`using`声明显式引入派生类作用域。 3. **参数无关性**:即使参数列表不同(区别于重载),只要名称相同即触发隐藏。 #### 三、作用机制 1. **编译期名称查找** C++编译器在派生类作用域中查找函数时,优先匹配派生类定义的函数。若找到同名函数,则停止向外层作用域(基类)搜索,导致基类函数隐藏。 ```cpp class Base { public: void func(int x) { } // 基类函数 }; class Derived : public Base { public: void func(double x) { } // 隐藏基类func(int) }; Derived d; d.func(10); // 调用Derived::func(double) d.func(10.5); // 调用Derived::func(double) // d.Base::func(10); // 需显式指定作用域才能调用基类函数 ``` 2. **与函数重载的对比** 重载要求函数在同一作用域内,而隐藏涉及不同作用域。若需要保留基类重载函数,需使用`using`声明: ```cpp class Derived : public Base { public: using Base::func; // 引入基类func void func(double x) { } // 现在基类和派生类函数形成重载 }; ``` #### 四、与重写(Override)的区别 | 特性 | 函数隐藏 | 函数重写 | |--------------|------------------------|------------------------| | 基类函数要求 | 非虚函数 | 虚函数 | | 多态性 | 不支持 | 支持 | | 参数列表 | 可不同 | 必须相同 | | 作用域 | 不同作用域(继承关系) | 同一虚函数表体系 | #### 五、典型应用场景 1. **屏蔽基类方法** 当派生类需要完全替换基类的某个方法逻辑时(即使参数不同)。 2. **接口限制** 在派生类中禁止使用基类的某些方法,例如: ```cpp class ReadOnlyBuffer : public Buffer { public: // 隐藏基类的write()方法 void write() = delete; // C++11特性 }; ``` #### 六、注意事项 1. **意外隐藏问题** 派生类新增函数可能与基类重载函数同名,导致基类所有重载版本被隐藏: ```cpp class Base { public: void log(int x) { } void log(string s) { } // 重载函数 }; class Derived : public Base { public: void log(double x) { } // 隐藏Base::log(int)和Base::log(string) }; ``` 2. **解决方案** 使用`using Base::log;`显式引入基类重载函数在调用时指定作用域。 #### 七、总结 函数隐藏体现了C++的**静态绑定**特性,其行为由编译期决定。理解这一机制有助于避免因名称冲突导致的意外错误,同时也能更灵活地设计类层次结构。在实际开发中,若需要实现运行时多态性,应优先使用虚函数机制[^1][^2];若需要完全替换接口,则可通过隐藏实现控制。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值