美文网首页
四、函数重载和函数指针

四、函数重载和函数指针

作者: 木鱼_cc | 来源:发表于2018-06-03 18:42 被阅读0次

    函数重载(Function Overload):用同一个函数名定义不同的函数,当函数名和不同的参数搭配时函数的含义不同。

    在C语言中,无法实现重载,只能使用函数指针

    void func(int a)
    {
       cout<<"func"<<endl;
       cout<<a<<endl;
    }
    
    int main(void)
    {
       //定义一个 指向void func(int a)的函数指针
       void (*fp)(int) = func;//fp就是执行void()(int)这种函数类型的指针
       //第二个()代表指定参数类型
       fp(10);
    
    }
    
    

    1.重载规则

    • 函数名相同。
    • 参数个数不同,参数的类型不同,参数顺序不同,均可构成重载。
    • 返回值类型不同则不可以构成重载。
    //函数重载,就是对参数列表的变换,不是函数返回值的变化
    //返回值必须一样,参数列表不同,并且函数名相同的函数都是重载函数
    //如果说函数重载加上了默认参数,并且函数名相同,就出现二义性
    //记住:函数重载最好不要有默认参数
    void func(int a);//ok
    void func(char a);//ok
    void func(char a,int b);//ok
    void func(int a, char b);//ok
    char func(int a);//与第一个函数有冲突
    

    2.调用准则

    编译器调用重载函数的准则:

    • 将所有同名函数作为候选者
    • 尝试寻找可行的候选函数

    精确匹配实参

    • 通过默认参数能够匹配实参
    • 通过默认类型转换匹配实参

    匹配失败

    • 最终寻找到的可行候选函数不唯一,则出现二义性,编译失败。
    • 无法匹配所有候选者,函数未定义,编译失败。

    3.重载底层实现(name mangling)

    C++利用 name mangling(倾轧)技术,来改名函数名,区分参数不同的同名函数。

    实现原理:用vcifld表示 **void char int float long double **及其引用。

    void func(char a);//func_c(char a)
    void func(char a,int b, double c);//func_cid(char a, int b, double c)
    

    4.函数指针

    定义函数指针
    void func(int a,int b)
    {
       cout<<a<<b<<endl;
    }
    
    void func(int a,int b,int c)
    {
       cout<<a<<b<<c<<endl;
    }
    
    void func(int a,int b,int c,int d)
    {
       cout<<a<<b<<c<<d<<endl;
    }
    
    //1.定义一个函数类型
    typedef void(myfunctype)(int ,int);//定义一个函数类型,返回值是void,参数列表是int,int,  void()(int,int)
    
    //2.定义一个函数指针类型
    typedef void(*myfunctype_pointer)(int,int);//定义了一个函数指针类型,返回值是void,参数列表是int,int,  void()(int,int)
    
    int main(void)
    {
       //1.定义一个函数指针
         myfunctype *fp1 = NULL;
         fp1 = func;
         fp1(10,20);
    
        //2.定义一个函数指针
         myfunctype_pointer fp2 = NULL;
         fp2 = func;
         fp2(10,20);
    
        //3.直接定义一个函数指针
         void(* fp3)(int,int) = NULL;
         fp3 = func;
         fp3(10,20);
    
         cout<<"---------------------------------------------"<<endl;
    
        //此时fp3是void(*)(int,int)
    //    fp3(10,20,30,40);//fp3是恒定指向一个函数入口,值指向了(int,int)
    //    fp3(10,20,30);//想通过函数指针,发生函数重载,是不可能的!!
        fp3(10,20);
    
         void(* fp4)(int,int,int) = func;//在对函数指针赋值的时候,函数指针会根据自己的类型,找到一个重载函数
         fp4(10,10,10);
         return 0;
    }
    
    

    5.重载总结

    • 重载函数在本质上是相互独立的不同函数。
    • 函数的函数类型是不同的
    • 函数返回值不能作为函数重载的依据
    • 函数重载是由函数名和参数列表决定的。

    相关文章

      网友评论

          本文标题:四、函数重载和函数指针

          本文链接:https://www.haomeiwen.com/subject/laijsftx.html