代码之家  ›  专栏  ›  技术社区  ›  oz10

const<type>&foo()与<type>foo()的比较

  •  3
  • oz10  · 技术社区  · 16 年前

    在一个 非模板 类中的函数返回签名 const <type>& foo(); 对战 <type> foo(); ?哪里 <type> 是一种内在类型。如果呢 <类型& GT; 是类/结构对象吗?

    对函数是否 常量 与众不同: const <type>& foo() const; <type> foo() const;

    例如,在非模板类中,非模板函数:

    const int& foo() const { return member_variable_; }
    

    对战

    int foo() const { return member_variable_; }
    
    5 回复  |  直到 16 年前
        1
  •  3
  •   Jason Govig    16 年前

    对于基元类型,只需按值返回。没有理由通过常量引用返回原语。

    对于非基元类型,这取决于。

    如果返回的值是函数的局部变量,则必须按值返回。否则,在调用方使用返回的引用之前,变量将被销毁。

    如果返回的值是类数据成员,则可以选择。

    按常量引用返回可避免复制,这可能是性能优势。但是,它将接口绑定到实现,即数据成员和返回值必须是同一类型。它也不太安全,因为调用方可以保留比对象生存期更长的引用,例如:

    const X& x = y->foo();
    delete y;
    // use x, oops!
    

    按值返回会产生一个或两个副本,这取决于您是否可以利用返回值优化(这可能适用于类似这样的简单get()方法)。此外,使用默认复制构造函数的对象副本可以更有效地复制(想想:编译器可以简单地存储数据)。

    建议:从return by value开始,在确定调用/副本是已知的性能问题之后,才切换到return by const引用。

    最后,另一种选择是按参数返回,这对于更复杂的对象(例如字符串)很有用:

    void foo(X& return_val) { return_val = member_variable_; }
    

    或:

    void foo(X* return_val) {
        assert(return_val != 0);
        *return_val = member_variable_;
    }
    
        2
  •  0
  •   anon    16 年前

    如果需要返回值,则必须返回值-const引用不是可接受的替换。但我怀疑你是在问这样的事情:

    struct A {
       X x;
        ...
       X f1() { return x; }
       const X & f2() { return x; }
    };
    

    我从来没有想出一个万无一失的指导方针。

        3
  •  0
  •   stefanB    16 年前
    const <type>& foo();
    

    类中可能有一个类似于资源的元素容器,并且 foo() 返回特定元素,如果您知道资源将足够长时间可用,则可以返回对容器中元素的常量引用,从而避免不必要的数据分配/复制。 可能是 const 如果不希望通过 英尺() 那就继续。也许你有一个例子,你想修改资源,需要做一些额外的工作,你会使非常量。你可以在你的api中两者都有,用户将根据用例来选择。

    <type> foo();
    

    返回资源的新副本 <type> . 这意味着一个副本。这对于简单数据或可能共享值的地方很好,并且您希望确保 <类型& GT; 是独立的-非共享的,就像一些字符串或int。

        4
  •  0
  •   Klaim    16 年前

    这完全取决于你到底想做什么。

    如果要返回对要由用户代码使用的对象的引用,则:

    <type>& foo()  { ... }
    

    如果要以只读方式返回对对象的引用,并且只允许访问此对象类型的常量函数,则:

    const <type>& foo() { ... }
    

    如果要返回对要由用户代码使用的对象的引用,即使类实例以只读方式(const)使用,则:

    <type>& foo() const { ... }
    

    如果您不想以只读方式返回对对象的引用,只允许访问此对象类型的const函数,并且如果类实例以只读方式使用(作为const),则:

    const <type>& foo() const { ... }
    

    只需添加一个警告:不要返回对函数变量的引用,它们在函数之外不存在…

        5
  •  0
  •   Todd Gardner    16 年前

    如果类型是内部类型,则传递const refs不会提高性能,并且可能会降低性能,而且安全性也会降低;最好选择按值传递和返回。我不是很喜欢asm,但据我所知,通过引用return意味着该值不能存储在寄存器中,因为它需要一个返回地址,因此可以禁用一些其他有用的优化;不过,我对此并不肯定。

    如果它是类或结构,则取决于值的生存期;如果它是函数的本地值,则无法返回它;否则,如果它是类成员,则我更喜欢const type&return,因为它可以通过避免复制构造函数来提供更好的性能。(观点不同,因为按价值计算更安全)。它还使您不必实现复制构造函数或使用可能有害的默认值,这很好。

    推荐文章