My understanding is that a reference type is neither
copy-constructible nore assignable. It is not copy-constructible
because althought reference can be viewed as a constan-pointer, it is
more of a syntax sugar in some circumstance, and will be optimized away
by compilers. Then there is no "copy construction" problem there. As
for assignable, it is obvious that the value of a reference itself
cannot be changed. Is is right?
Thanks,
Andy
[ See http://www.gotw.ca/resources/clcm.htm for info about ]
[ comp.lang.c++.moderated. First time posters: Do this! ]
I am having problems with grasping what you are asking. A reference has
to be bound to a suitable object whose type may or may not be the same
as the type the reference is to. We call the type the reference is to
the 'static' type of the reference and the type of the object referred
to as the 'dynamic' type of the reference. Copy construction is selected
at compile time and so will use the static type. This may result in
slicing (using only the base type of a derived object).
struct base {
int i;
};
struct derived: public base {
int j;
derived(){}
derived(base const & b)(i = b.i); // without this you cannot
init a derived with a base object or a base& reference
};
int main(){
derived d;
d.i = 1;
d.j = 2;
base & b_ref(d); // OK
base & b1_ref(b); // OK
base b1(d); // OK but only copies b.i
derived d1(b_ref); // OK but does not copy j
// etc.
};
Now where is the problem?
--
Francis Glassborow ACCU
Author of 'You Can Do It!' see http://www.spellen.org/youcandoit
For project ideas and contributions: http://www.spellen.org/youcandoit/projects
If type is understood to mean classes (structs), template classes
(structs) and primitive types, then there are no reference types in
C++, unlike Java or C#.
> It is not copy-constructible
> because althought reference can be viewed as a constan-pointer, it is
> more of a syntax sugar in some circumstance, and will be optimized
away
> by compilers. Then there is no "copy construction" problem there.
The choice of making a class copy-constructible is the choice of a
programmer. To make it uncopiable, you can declare its copy constructor
private without defining it.
> As for assignable, it is obvious that the value of a reference itself
> cannot be changed. Is is right?
It is true that you cannot change the value of a reference - only the
content it points to can be changed for a non-const references.
Cheers,
>>My understanding is that a reference type is neither
>>copy-constructible nore assignable. It is not copy-constructible
>>because althought reference can be viewed as a constan-pointer, it is
>>more of a syntax sugar in some circumstance, and will be optimized away
>>by compilers. Then there is no "copy construction" problem there. As
>>for assignable, it is obvious that the value of a reference itself
>>cannot be changed. Is is right?
>
>
> I am having problems with grasping what you are asking. A reference has
> to be bound to a suitable object whose type may or may not be the same
> as the type the reference is to. We call the type the reference is to
> the 'static' type of the reference and the type of the object referred
> to as the 'dynamic' type of the reference. Copy construction is selected
> at compile time and so will use the static type. This may result in
> slicing (using only the base type of a derived object).
Although the discussion is only hypothetical in nature, and I'm not
entirely sure about the fine details of the standard on this, I have
a problem with this last statement... You're mixing the notion of
copy-construction of a reference with copy-construction of the object
the reference refers to.
Copy-construction of a reference is something that does happen the
way the language is -- what I'm not sure is if it is called that, or
if it even is correct to call it that.
If you are inside a function that received parameter X by reference
(to an int), and you want to call another function that receives a
reference to an int, the compiler "creates a copy" of the reference
you received and passes that copy to the other function -- both
"copies" of the reference refer to the same object (polymorphism is
not a problem here -- both references have the same static type and
the same dynamic type).
In terms of typical implementation, a compiler should deal with that
reference exactly as it would deal with a pointer. And it *does need*
to create an extra copy of that "pointer" to be passed to the other
function (assuming that inlining is out of the picture in that
particular situation).
So, in practical terms, there is such thing as copy-construction of
a reference.
Assignment of the reference of course can not be possible, since that
contradicts the very definition of references.
Carlos
--
Assignable ... you cannot "reseat" a reference, so it is not
assignable. But again, this word usually means if you can write codes
like "a=b" ... and references do allow that! (albeit in a different way
than you might want)
Samee
It would be incorrect to refer to references to any kind of objects as
"reference types" in C++. "Copy-constructible" should not be understood
to mean anything other than an operation that entails a call to a copy
constructor.
> Copy-construtible usually refers to the ability to construct an
object
> from another of the same type without changing the original - and
> references can be "constructed" from another reference of the same
type
> - so you might call it copy constructible. The fact remains, it
doesn't
> call any constructor ... so you can figure out what you want to call
> it.
May be the OP can reappear and let us know if we have clarified all his
doubts or made him even more doubtful.
>
> Assignable ... you cannot "reseat" a reference, so it is not
> assignable. But again, this word usually means if you can write codes
> like "a=b" ... and references do allow that! (albeit in a different
way
> than you might want)
>
I feel the a reference in C++ and a reference type (not in C++ but
other technologies like Java) cannot be considered equivalent. Sorry
for assuming but the OP I feel referred to the latter type, not being
completely sure whether such a viewpoint/classification/phenomenon
exists in C++ or not.
Cheers,
Andy (not the OP)
> Assignable ... you cannot "reseat" a reference, so it is not
> assignable. But again, this word usually means if you can write codes
> like "a=b" ... and references do allow that! (albeit in a different way
> than you might want)
The word "assignable" with regard to the standard library does NOT mean
"can be written as a = b". The reauirement in 23.1 requires that the
two objects be equivelent after the assignment. Applying the assignment
operator to a reference does not make it the equivelent to the reference
on the right hand side. Only the referred to objects are copied.
Further, references are NOT copy constructoable (from 20.1.3). While
the construction requirements are met, the destruction is not.
"Reference type" in C++ just means a type of reference, e.g. int &.
--
Ben Hutchings
Having problems with C++ templates? Your questions may be answered by
<http://womble.decadentplace.org.uk/c++/template-faq.html>.
23.1/4 Table 64 -- Assignable requirements:
expression: t=u
return type: T&
post-condition: t is equivalent to u
The word "equivalent" appears 134 times (including examples and notes,
but not counting two times in the index) but none of these appear to be
a definition. The closest I found was 23.1.2/3, which talks about
associative containers:
...two keys k1 and k2 are considered to be equivalent if for
the comparison object comp,
comp(k1,k2)==false && comp(k2,k1)==false .
Recall that the default comparison object is std::less. Thus, after
t=u, t and u are equivalent if !(t<u) and !(u<t).
I don't know if I would consider Samee Zahur right or not... but he
at least has a point.
> Further, references are NOT copy constructoable (from 20.1.3). While
> the construction requirements are met, the destruction is not.
Right. Also, &t doesn't return a T* that denotes the address of the
reference.
> the construction requirements are met, the destruction is not.
Thanks for the info. I will need to rely on this group until I get a
copy of the standard for myself ... until then, these corrections are
all I got:)
And ... I thought reference IS a different type! Why do then they say
that it isn't ... I often see things like "to be considered an alias
only" kind of things in this group! I really prefer thinking of
references as a syntatically nice but funcitonally limited pointer ...
have I got my concepts mixed up or something?
Samee
Samee
> The word "equivalent" appears 134 times (including examples and notes,
> but not counting two times in the index) but none of these appear to be
> a definition. The closest I found was 23.1.2/3, which talks about
> associative containers:
The type here is a reference. You can't have reference to reference
so the assignable requirements are NOT met before you get to rest
of the statements. Equivelence, while perhaps not well defined,
is more than just the result of the comparison operator. Comparison
need not even be defined for assignable types in sequences. So
we have to go to a more common sense. Would you consider two
references that refer to different objects to be equivelent?
I don't know what a "reference type" is in C++,
and I think that using this term just leads people astray,
especially those with a background in Java.
Copy construction, etc., apply to objects, not names, and
there is no such thing as an object with a type with the word
"reference" in it. Thus, the question of "copy construction",
"assignment",
etc., of "reference types" is moot. There is only "assignment", etc.,
of objects.
As for "the value of a reference itself", this is meaningless in C++.
A reference is an alternate name for an object. It is not an object.
Anything you do to a reference, once the reference is declared,
refers to the object it refers to. If you write
A a; A &ra = a;
then "ra" is just another name for "a". Despite the fact that the
two declarations have similar syntax, the first declaration creates
an object, but the second does not. If you write
A a; A *pa = &a;
then "*pa" is also just another name for "a". "pa" is an object
of type "pointer to A", but "*pa" is (effectively) another name
for the object denoted by "a"; that is what we mean when we say
"*pa is a reference to A".
If you later have:
A &rpa = *pa;
"rpa" will just be another name for the object "*pa" referred to
when this declaration was "executed."
This is what "reference" means in the current C++. Please keep
in mind that other languages, such as Java and Algol-68 use the
word to refer to a different concept.
The fact that it is, with the currently popular computer architectures,
sometimes convenient to use a pointer to implement reference behavior
does not mean a reference is "really a pointer."
-- Alan McKenney
>
> And ... I thought reference IS a different type! Why do then they say
> that it isn't ... I often see things like "to be considered an alias
> only" kind of things in this group! I really prefer thinking of
> references as a syntatically nice but funcitonally limited pointer ...
> have I got my concepts mixed up or something?
>
References are a type. Reference objects may however not exist however.
Declaration of a variable, member variable, function parameter or
return value with reference type affects its initialisation and, in
the case of a return value, whether it is an lvalue or an rvalue.
Aside from that, anything declared with type T & is treated much the
same as if it had type T. A named reference bound to a named object
or function behaves like the original name, hence the description as
an "alias".
--
Ben Hutchings
Having problems with C++ templates? Your questions may be answered by
<http://womble.decadentplace.org.uk/c++/template-faq.html>.
[ See http://www.gotw.ca/resources/clcm.htm for info about ]
> I don't know what a "reference type" is in C++,
> and I think that using this term just leads people astray,
> especially those with a background in Java.
What leads people astray is people trying to explain references
who don't seem to understand it. About half of your message
is entirely incorrect.
>
> Copy construction, etc., apply to objects, not names, and
> there is no such thing as an object with a type with the word
> "reference" in it.
The above statement is entirely false. Names are names, types
are types. Reference is a type. You can have a reference
without a name (just like any other type).
References are Compound Types as defined in 3.9.2 of the standard
and further elaborated in 8.3.2. Referencers are objects. They're
odd objects, but they are objects.
They do however fail to meet the precise definition of assignable and
copy-constructable objects in the later sections of the standard.
>There is only "assignment", etc., of objects.
References are objects.
>
> As for "the value of a reference itself", this is meaningless in C++.
Well, it has initialization, it's just unmodifable after modified (like
any other const object).
> A reference is an alternate name for an object. It is not an object.
It is an object. It is not a name.
> Anything you do to a reference, once the reference is declared,
> refers to the object it refers to
Once it is initialized.
> References are objects.
[...]
> It is an object. It is not a name.
This is in contradiction of the C++ Standard:
1.8/1
"An object is a region of storage."
8.3.2/3
"It is unspecified whether or not a reference requires storage (3.7)."
8.3.2/1
"Note: a reference can be thought of as a name of an object."
--
Gerhard Menzl
#dogma int main ()
Humans may reply by replacing the thermal post part of my e-mail address
with "kapsch" and the top level domain part with "net".
It is explicitly mentioned in the standard (e.g. in 5.3.4/1, and
probably somewhere else too) that references are not objects. References
cannot be created by new-expressions (5.3.4/1), and it is even
unspecified whether or not a reference requires storage (8.3.2/3).
--
Seungbeom Kim
> Alan McKenney wrote:
>
> > I don't know what a "reference type" is in C++,
> > and I think that using this term just leads people astray,
> > especially those with a background in Java.
>
> What leads people astray is people trying to explain references
> who don't seem to understand it. About half of your message
> is entirely incorrect.
>
> >
> > Copy construction, etc., apply to objects, not names, and
> > there is no such thing as an object with a type with the word
> > "reference" in it.
>
> The above statement is entirely false. Names are names, types
> are types. Reference is a type. You can have a reference
> without a name (just like any other type).
>
> References are Compound Types as defined in 3.9.2 of the standard
> and further elaborated in 8.3.2. Referencers are objects. They're
> odd objects, but they are objects.
[snip]
After many years and many loong threads, nobody has submitted a DR for
the note in 5.3.4, or for 3.9/9's implication that references do
not have object type. So, they might be objects, but so far no-one
thinks this is important enough to go in the standard. :-)
>
> After many years and many loong threads, nobody has submitted a DR for
> the note in 5.3.4, or for 3.9/9's implication that references do
> not have object type. So, they might be objects, but so far no-one
> thinks this is important enough to go in the standard. :-)
You'd have to further go back and define object in terms of things of
"object type." The problem occurs is that the language allows
references as function parameters and as members of classes and
it's hokie if you remove it's object status in these instasnces.
Certainly, name is clearly defined. Objects are not "name" in
the defined use of that term. The non-normative passages might
be advised to use a different word to describe the relationship
of a reference to it's referred-to object.
It then goes on to enumerate that this isn't a total definition as
functions aren't objects even if they do occupy storage.
>
> 8.3.2/3
> "It is unspecified whether or not a reference requires storage (3.7)."
Many other objects like int and pointers in cretain circumstances don't
require storage either.
> 8.3.2/1
> "Note: a reference can be thought of as a name of an object."
>
NOTES are not normative. This is a simile that is outside the
standard. The fact that it's a note (and it's wishy washy "can
be thought of" phrase should have been a hit.
Evidently, the question of whether references are "objects" is
turning into a religious argument. I'll try to supply a few
falsifiable[*] observations, and then take a vow of silence (until
the
next thread, at least :-) :-))
1. People can say that references are objects, if they wish.
They certainly seem to be doing so, and no one has stopped
them.
My own opinion is that it's a little like calling a [dog's]
tail
a leg, but I don't expect to change anyone's mind.
Here's where a reference differs from most kinds of objects:
2. There are a limited number of contexts in which one can
"create" a reference (I use the term "create" to sidestep the
religious issue of whether references implicitly have a
constructor):
a. A declaration, e.g., T &rt = {lvalue expression};
b. Function arguments.
c. As a return type, where the return value is an lvalue.
d. Dereferencing a pointer. (I'm including C array element
reference, since a[b] is defined as *(a + b) )
3. You can't create an object of reference type with "new".
That is, "new T&" is a syntax error.
4. You cannot define a constructor or destructor for a reference
type.
You can say that the system supplies them, I suppose.
5. Once created, all uses of a reference affect the underlying
object. There is currently no syntax by which one could
even indicate the desire to "reseat" a reference.
6. Once created, there's no way your program can tell whether
it is dealing with a reference. By that I mean, if you have
T t; T &rt = t; T *pt = &t;
then t, rt, and *pt will behave identically, since they
are all lvalues and refer to the same object.
This is not to say that the types T, T&, and/or T* are
interchangeable -- they aren't.
7. You can't get the address of a reference (as opposed to its
underlying object.)
Pointer to reference to T and reference to reference to T
are currently illegal. From what I'm hearing, if they are ever
made legal, they will be treated as pointer to T and reference
to T, resp.
Basically, a reference is missing most of the capabilities that we
generally associate with objects.
Some of us consider it less confusing to say, "don't think of a
reference
as an object, just think of it as a language feature with the
following
features" than to call it an object and then explain the myriad
ways
it doesn't act like other objects.
-- Alan McKenney
[*] "Falsifiable" statements are those which can be objectively
established
to be true or false.
E.g., "the universe is full of x-particles, which
don't interact in any way, shape, or form with normal matter or
energy"
is not falsifiable, but "the universe is full of neutrinos, which
interact with normal matter and energy in the following ways" is.
>>This is in contradiction of the C++ Standard:
>>
>>1.8/1
>>"An object is a region of storage."
>
>
> It then goes on to enumerate that this isn't a total definition as
> functions aren't objects even if they do occupy storage.
"[Note: A function is not an object, regardless of whether or not it
occupies storage in the way that objects do.]"
Notes are not normative. *g* The sentence does not weaken the preceding
definition in any way, it merely points out that the reverse conclusion
is not valid. Whether functions are objects or not is irrelevant in this
context.
>>8.3.2/3
>>"It is unspecified whether or not a reference requires storage (3.7)."
>
>
> Many other objects like int and pointers in cretain circumstances
> don't require storage either.
In what sense?
>>8.3.2/1
>>"Note: a reference can be thought of as a name of an object."
>>
>
>
> NOTES are not normative. This is a simile that is outside the
> standard. The fact that it's a note (and it's wishy washy "can
> be thought of" phrase should have been a hit.
I never said it was normative, I merely pointed out the contradiction.
Notes are used to explain the intention behind the Standard, and to
clarify normative text. The are not nonsense (or wishy washy).
--
Gerhard Menzl
#dogma int main ()
Humans may reply by replacing the thermal post part of my e-mail address
with "kapsch" and the top level domain part with "net".
[ See http://www.gotw.ca/resources/clcm.htm for info about ]
I really don't see that they are.
A parameter can be "an object or reference..." (1.3/9), implying
references are distinct from objects. The same distinction is
made in 3.5 and 8.5.
"Object type" is the type of an object (1.8/1), and reference types
aren't object types (3.9/9).
An object of type T has object representation of size sizeof(T),
according to 3.9/4, but of course this is not the case for a
reference type (5.3.3/2).
However, the description of declarations fails to distinguish
references in various places (at least 7.1.1 and 8/1), so arguably the
meaning of "object" in the standard is somewhat context-dependent.
--
Ben Hutchings
Having problems with C++ templates? Your questions may be answered by
<http://womble.decadentplace.org.uk/c++/template-faq.html>.
[ See http://www.gotw.ca/resources/clcm.htm for info about ]