May 20th Wednesday (五月 二十日 水曜日)

本文探讨了C++中使用引用参数时临时变量的生成情况,解释了为何限制const引用,并提供了实例说明。重点阐述了临时变量在不同场景下的作用与限制,以及如何合理使用const关键字保护数据完整性。

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

Temporary Variables, Reference Arguments, and const

  C++ can generate a temporary variable if the actual argument doesn't match a reference argument. Currently,
C++ permits this only if the argument is a const reference, but this is a new restriction. Let's look at the cases
in which C++ does generate temporary variables and see why the restriction to a const reference makes sense.

  First, when is a temporary variable created? Provided that the reference parameter is a const, the compiler
generates a temporary variable in two kinds of situations:

* The actual argument is the correct type, but isn't an Lvalue
* The actual argument is of the wrong type, but of a type that can be converted to the correct type

void swapr(int & a, int & b)  // use references
{
    int temp;

    temp = a;      // use a, b for values of variables
    a = b;
    b = temp;
}

double refcube(const double &ra)
{
     return ra * ra * ra;
}

Now consider the following code:

double side = 3.0;
double * pd = &side;
double & rd = side;
long edge = 5L;
double lens[4] = { 2.0, 5.0, 10.0, 12.0} ;
double c1 = refcube(side);          // ra is side
double c2 = refcube(lens[2]);       // ra is lens[2]
double c3 = refcube(rd);            // ra is rd is side
double c4 = refcube(*pd);           // ra is *pd is side
double c5 = refcube(edge);          // ra is temporary variable
double c6 = refcube(7.0);           // ra is temporary variable
double c7 = refcube(side + 10.0);   // ra is temporary variable

  The arguments side, lens[2], rd, and *pd are type double data objects with names, so it is possible to
generate a reference for them, and no temporary variables are needed. (Recall that an element of an array
behaves like a variable of the same type as the element.) But edge, although a variable, is of the wrong type.
A reference to a double can't refer to a long. The arguments 7.0 and side + 10.0, on the other hand, are
the right type, but are not named data objects. In each of these cases, the compiler generates a temporary,
anonymous variable and makes ra refer to it. These temporary variables last for the duration of the function
call, but then the compiler is free to dump them.

  What would happen if we did the following under the freer rules of early C++?

long a = 3, b = 5;
swapr(a, b);

  Here there is a type mismatch, so the compiler would create two temporary int variables, initialize them to 3 and 5,
and then swap the contents of the temporary variables, leaving a and b unaltered.

  In short, if the intent of a function with reference arguments is to modify variables passed as arguments, situations
that create temporary variables thwart that purpose. The solution is to prohibit creating temporary variables in these
situations, and that is what the C++ standard now does. (However, some compilers still, by default, issue warnings
instead of error messages, so if you do see a warning about temporary variables, don't ignore it.)

  Now think about the refcube() function. Its intent is merely to use passed values, not to modify them, so temporary
variables cause no harm and make the function more general in the sorts of arguments that it can handle. Therefore, if
the declaration states that a reference is const, C++ generates temporary variables when necessary. In essence, a C++
function with a const reference formal argument and a nonmatching actual argument mimics the traditional passing by value
behavior, guaranteeing that the original data is unaltered and using a temporary variable to hold the value.

Remember

  If a function call argument isn't an Lvalue or does not match the type of the corresponding const reference parameter,
C++ creates an anonymous variable of the correct type, assigns the value of the function call argument to the anonymous
variable, and has the parameter refer to that variable.

Use const When You Can

  There are three strong reasons to declare reference arguments as references to constant data:

  * Using const protects you against programming errors that inadvertently alter data.
  * Using const allows a function to process both const and non-const actual arguments, while a function omitting const in
   the prototype only can accept non-const data.
  * Using a const reference allows the function to generate and use a temporary variable appropriately.

  You should declare formal reference arguments as const whenever it's appropriate to do so.

  Typically, the reference refers to a reference passed to the function in the first place, so the calling function actually
winds up directly accessing one of its own variables.

Remember

  A function that returns a reference is actually an alias for the referred-to variable.

  You can assign a value (including a structure or a class object) to a C++ function only if the function returns a reference
to a variable or, more generally, to a data object. In that case, the value is assigned to the referred-to variable or data object.

  There are two main reasons for using reference arguments:

  * To allow you to alter a data object in the calling function
  * To speed up a program by passing a reference instead of an entire data object

  The second reason is most important for larger data objects, such as structures and class objects.

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值