C++;同时接受指针和引用的函数 我在C++中编写了一个库,并具有一些与模块一起工作的功能。示例如下所示: void connect(Module *a, Module *b);

C++;同时接受指针和引用的函数 我在C++中编写了一个库,并具有一些与模块一起工作的功能。示例如下所示: void connect(Module *a, Module *b);,c++,pointers,reference,overloading,C++,Pointers,Reference,Overloading,问题是,如果函数也接受引用(一些模块可能在堆栈上分配,一些在堆上分配,所有的&s和*s很快就会变得无聊和混乱),那么它有时会很方便 现在我有了内联函数,它接受引用,将它们转换为指针并调用原始函数 inline void connect(Module &a, Module &b){ connect(&a, &b); } 我不太喜欢这个解决方案,因为对于更多的函数,它会产生大量的代码来编写、读取、编译 考虑的另一件事是添加Module::operator M

问题是,如果函数也接受引用(一些模块可能在堆栈上分配,一些在堆上分配,所有的&s和*s很快就会变得无聊和混乱),那么它有时会很方便

现在我有了内联函数,它接受引用,将它们转换为指针并调用原始函数

inline void connect(Module &a, Module &b){
    connect(&a, &b);
}
我不太喜欢这个解决方案,因为对于更多的函数,它会产生大量的代码来编写、读取、编译

考虑的另一件事是添加
Module::operator Module*()
,它将返回
this

你对此有何看法?难道没有我错过的史诗般的失败的可能性吗


谢谢。

为什么不直接用

connect(&a, &b);

就像在你的内联函数中,当你必须用引用调用它时?这非常清楚地表明,函数使用指针,
a
b
不是指针。您只需再键入两个字符。

为什么不使用

connect(&a, &b);

就像在你的内联函数中,当你必须用引用调用它时?这非常清楚地表明,函数使用指针,
a
b
不是指针。您只需再键入两个字符。

任何时候使用运算符重载,都会增加epic失败的可能性。问题是,您知道,您并不是指将
*
作为标准指针运算符,但天真地阅读您的代码的人却不是


最好的解决方案是返回并重构/重新思考代码,这样就不需要为同一个操作使用两个接口,

每当使用运算符重载时,都会增加epic失败的可能性。问题是,您知道,您并不是指将
*
作为标准指针运算符,但天真地阅读您的代码的人却不是


最好的解决方案是返回并重构/重新思考代码,这样您就不需要为同一个操作使用两个接口,

我不太愿意做这样的事情-这可能是一个令人困惑的接口


一般来说,我更喜欢使用常量引用的接口,但是,如果传入的对象将被修改,我倾向于使用指针而不是非常量引用,因为它给接口用户一个指示,表明传入的对象可能会被修改。

我非常不愿意做这样的事情-使用它可能会使接口混乱


一般来说,我更喜欢使用常量引用的接口,但是,如果传入的对象将被修改,我倾向于使用指针而不是非常量引用,因为它向接口用户提供了一个指示,表明传入的对象可能被修改。

需要两个函数的原因是,指向模块的指针与指向模块的引用的指针的类型基本不同。这是绕不开的

对我来说,指针是坏的。总是。只有当你需要某物的地址而不是某物的引用时才使用它们。而且很少需要对象的实际地址。我会做以下几件事:

  • 将基于指针的函数转换为基于引用的函数
  • 在不必要的地方停止使用指针。您当然应该避免使用指针和引用

  • 此外,您可能还需要研究常量。

    之所以需要两个函数,是因为指向模块的指针与对模块的引用基本上是不同的类型。这是绕不开的

    对我来说,指针是坏的。总是。只有当你需要某物的地址而不是某物的引用时才使用它们。而且很少需要对象的实际地址。我会做以下几件事:

  • 将基于指针的函数转换为基于引用的函数
  • 在不必要的地方停止使用指针。您当然应该避免使用指针和引用

  • 此外,您可能需要研究常量。

    正如您所观察到的,您可以重载函数以获取指针或引用,但我会拒绝这样做,因为这仅仅是出于方便,并且只支持一个函数—所有主要库都是这样工作的

    在该函数中使用哪种参数类型?这取决于我的个人指导原则:

    • 如果空对象有意义,请使用指针

    • 如果常见的用例是被传递的对象通常是动态创建的,那么使用指针

    • 如果实现在内部使用指针,请使用指针

    • 否则,请使用引用


    正如您所观察到的,您可以通过重载函数来获取指针或引用,但我会拒绝这样做,因为这仅仅是出于方便,并且坚持使用一个函数—所有主要库都是这样工作的

    在该函数中使用哪种参数类型?这取决于我的个人指导原则:

    • 如果空对象有意义,请使用指针

    • 如果常见的用例是被传递的对象通常是动态创建的,那么使用指针

    • 如果实现在内部使用指针,请使用指针

    • 否则,请使用引用


      • 我会避免在公共API中内联

        在可能的情况下,const&优先于&or*

        我不知道这些东西是如何联系在一起的,也不知道a和b之间有什么关系

        void connect(Module *a, Module *b);
        
        将模块接口重新安排为更加明确是否有意义

        Module a;
        a.connectOutput(b);
        

        命名参数有助于上下文;)

        我会避免在公共API中内联

        在可能的情况下,const&优先于&or*

        我不知道这些东西是如何联系在一起的,也不知道a和b之间有什么关系

        void connect(Module *a, Module *b);
        
        将模块接口重新安排为mor有意义吗