[英]How to return a reference in C++
例如,如果我在函数中创建一个新对象,并且想返回其引用,该怎么做?
可以说我有一个IntClass,它的private中有一个'int num'字段。 所以我想在函数中创建一个IntClass的新元素,并返回该对象的引用。 我已经尝试过类似的操作,但是它似乎是非法的(出于某种原因,尽管这样做的原因是,尽管编译器本身没有错误(ECLIPSE),但是在编译代码时,二进制文件还是被删除了:
IntClass* a = new IntClass(10);
IntClass &ref = *a;
return ref;
有什么想法如何返回参考吗?
编辑:允许“假设” C ++使用垃圾回收
由于大多数人不清楚为什么我“想要”这样做,所以这里是完整的问题:
我得到了这个文件(不是我制作的,无法编辑):
poly_subtype.h :
#ifndef POLY_SUBTYPE_H
#define POLY_SUBTYPE_H
#include <iostream>
#include "cpu_add.h"
using std::cout;
using std::endl;
//Deriving classes definition
class IntClass;
class DoubleClass;
//The Virtual Number Class. IntClass and FloatClass will derive from this class.
class Number {
public:
//return a Number object that's the results of x+this, when x is DoubleClass
virtual Number& addDouble(DoubleClass& x) = 0;
//return a Number object that's the results of x+this, when x is IntClass
virtual Number& addInt(IntClass& x) = 0;
//return a Number object that's the results of x+this, when x is either
//IntClass or DoubleClass
virtual Number& operator+(Number& x) = 0;
//Print the number stored in the object
virtual void print_number() = 0;
};
class IntClass : public Number {
private:
int my_number;
public:
//Constructor
IntClass(int n):my_number(n) {}
//returns the number stored in the object
int get_number() {return my_number;}
//print the number stored in the object
void print_number() {cout << my_number << endl;}
//return a DoubleClass object that's the result of x+this
Number& addDouble(DoubleClass& x);
//return an IntClass object that's the result of x+this
Number& addInt(IntClass& x);
//return a Number object that's the result of x+this.
//The actual class of the returned object depends on x.
//If x is IntClass, then the result if IntClass.
//If x is DoubleClass, then the results is DoubleClass.
Number& operator+(Number& x);
};
class DoubleClass : public Number {
private:
double my_number;
public:
//Constructor
DoubleClass(double n):my_number(n) {}
//returns the number stored in the object
double get_number() {return my_number;}
//Print the number stored in the object
void print_number() {cout << my_number << endl;}
//return a DoubleClass object that's the result of x+this
Number& addDouble(DoubleClass& x);
//return a DoubleClass object that's the result of x+this
Number& addInt(IntClass& x);
//return a DoubleClass object that's the result of x+this.
//This should work if x is either IntClass or DoubleClass
Number& operator+( Number& x);
};
#endif
并且我已经有了这个文件(同样,不是我写的,也无法编辑-说我可以使用这些功能,但不能使用'+'运算符。
cpu_add.h:
#ifndef CPU_ADD_H
#define CPU_ADD_H
double add_double_double(double a, double b) {return (a+b);}
double add_int_double(int a, double b) {return ((double)(a)+b);}
int add_int_int(int a, int b) {return (a+b);}
#endif
我的目标是实现下一个功能(您可以在上面的poly_subtype.h中找到它们的声明和功能):
Number& IntClass::addInt(IntClass& x);
Number& IntClass::addDouble(DoubleClass& x);
Number& IntClass::operator+(Number& x);
Number& DoubleClass::addInt(IntClass& x);
Number& DoubleClass::addDouble(DoubleClass& x);
Number& DoubleClass::operator+(Number& x);
我希望现在更加清楚。
例如, AddInt :
Number& IntClass::addInt(IntClass& x){
int num = add_int_int(my_number, x.get_number());
IntClass* a = new IntClass(num);
IntClass &ref = *a;
return ref;
}
您的示例代码是等待发生的内存泄漏。 谁负责完成对象的删除? 返回引用(而不是指针)的事实使对象在堆上的分配变得不那么明显。 在某些时候,有人需要delete &obj;
,这很不合常理。
通常,您应该只返回对其他地方引用的对象的引用(例如,类成员或类成员指向的堆对象)。 在您的特定情况下,您最好执行以下操作:
IntClass myFunc()
{
...
return IntClass(10);
}
即按价值回报。
为什么首先要返回引用? 只是返回值而不是引用。 如果您担心的话,编译器通常会优化副本。
请参阅有效的C ++,条款21。
哦,我明白了。 您应该实现一个修改“ this”对象的变异操作,并返回对其的引用。 所以就像:
Number& YourNumber::Add(const YourNumber& pX) {
// do addition which mutates this...
return *this;
}
尽管您可以执行上面写的操作,但这是一个不好的尝试。 如果在免费存储区上分配了资源,则应返回指向该资源的指针,而不是引用。 更好的是,使用适当类型的智能指针:例如std::auto_pointer
(或更好的std/boost::unique_ptr
)(如果生产者未持有资源),而std::shared_ptr
(相反)。 您的代码示例是合法的,但是返回的引用的使用者不(也无法)知道如何处理返回的引用。
我可以想象在这种情况下返回对对象的常量引用:
class Producer {
std::shared_ptr<SomeObject> mObject;
public:
Producer() : mObject(new SomeObject) {}
const SomeObject& GetObject() const {
return *mObject;
}
};
但是,您可以返回对具有静态持续时间的对象的引用,但这有一些缺点-您无法(适当地)控制对象的生存期。例如:
SomeObject& GetSomeObjectSingletonReference() {
static SomeObject sInstance;
return sInstance;
}
干杯,
保罗
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.