I am learning C++ using the books listed here. My question is that is there a difference between a variable and an object. Consider the following example:
int i = 0; //i is an object of type int. Or we can say i is a variable of type int
int &refI = i; //refI is a "reference variable" of "reference type `int&`. But here refI is not an object.
My current understanding is that both of the terms variable and object overlaps to a large extent. But in some contexts like in case of refI above, there can be some differences. In particular, refI is a reference variable of reference type int& and refI is not an object because a reference is an alias for some other object. While i is both an object and a variable.
My question is that am i correctly analyzing the refI case above? If not, what does the standard say about this.
My second question is that, does the standard C++ strictly differentiate between these two terms. If yes, how and where. For example something like,
a variable may be defined as an object with a name. And any object without a name is not a variable.
Here the user says that a variable and object are different.
Edit
I am also asking this question because i am aware that in Python(as it is a dynamically typed language) there is a clear distinction between variables and objects. Does the C++ standard also make such a clear distinction.
Difference between an object and a variable in C++
Variable is a programming language level concept. A variable has a type and it (usually) has a name. A variable can denote an object, or a reference.
There's no concise definition for the meaning of "variable" in the standard nor a section dedicated to them alone, but closest individual rule to specifying its meaning is:
[basic.pre]
A variable is introduced by the declaration of a reference other than a non-static data member or of an object.
The variable's name, if any, denotes the reference or object.
Object is a concept in the level of the abstract machine that the language defines. It is mostly specified in the section "Object model [intro.object]" which begins:
[intro.object]
The constructs in a C++ program create, destroy, refer to, access, and manipulate objects.
An object is created by a definition, by a new-expression ([expr.new]), by an operation that implicitly creates objects (see below), when implicitly changing the active member of a union, or when a temporary object is created ([conv.rval], [class.temporary]).
An object occupies a region of storage in its period of construction ([class.cdtor]), throughout its lifetime, and in its period of destruction ([class.cdtor]).
int i = 0; //i is an object of type int. Or we can say i is a variable of type int
i is a variable of type int. The variable's name denotes an object.
int &refI = i; //refI is a "reference variable" of "reference type `int&`. But here refI is not an object.
refI is a variable of type int&. The variable's name denotes a reference. The reference is bound to the object named by i and can be seen as another name for the same object.
Your understanding seems to be correct. I'm going to reuse the quote from #RichardCritten answer, but with a different explanation.
[basic.pre]/6
A variable is introduced by the declaration of a reference other than a non-static data member or of an object.
The variable's name, if any, denotes the reference or object.
So a variable is one of:
A named object, e.g. int i = 1;. Non-static data members don't count. Functions don't count, since they're not objects, see below. Named objects are always created by declarations.
An unnamed object that has a declaration. The only ones I'm aware of are unnamed function parameters (and structured bindings, see below).
A named reference, e.g. int &j = i;. Non-static data members don't count. Named references are always created by declarations.
An unnamed reference that has a declaration. The only ones I'm aware of are unnamed function parameters (and structured bindings, see below). As far as I'm aware, there are no unnamed references without declarations, since expressions can't have reference types.
A structured binding: there's a single unnamed object or reference per structured binding (regardless of the number of identifiers), AND, if this structured binding was initialized with a std::tuple-like class (as opposed to an array or a class with magically detected members), there's also one reference per each member (unnamed, surprisingly - the identifiers magically refer to those references, they are not their names).
[intro.object]
The constructs in a C++ program create, destroy, refer to, access, and manipulate objects. An object is created by a definition, by a new-expression, by an operation that implicitly creates objects (see below), when implicitly changing the active member of a union, or when a temporary object is created. An object occupies a region of storage in its period of construction, throughout its lifetime, and in its period of destruction.
[Note 1: A function is not an object, regardless of whether or not it occupies storage in the way that objects do.
— end note]
The properties of an object are determined when the object is created. An object can have a name. An object has a storage duration which influences its lifetime. An object has a type.
The above explains what counts as an object.
But I find it easier to remember what isn't one:
Functions are not objects. (see quote above)
References are not objects. (again, note that expressions can't have reference types; there are no temporary unnamed references)
Prvalues are not objects (since C++17).
If the "object" doesn't exist, it isn't an object (i.e. if its lifetime hasn't started or has already ended, AND its constructor nor destructor are currently running).
Obviously, labels are not objects, and neither are macros.
Ignoring the language-lawyer tag since you are just learning. You don't need to know the exact wording of the standard to be able to understand the example you gave.
int i = 0; //i is an object of type int. Or we can say i is a variable of type int
int &refI = i; //refI is a "reference variable" of "reference type `int&`. But here refI is not an object.
Both i and refI are variables. Anything you give a name is a variable.
But both i and refI are also objects. Every variable has an address in memory where it lives and that makes it an object. There are objects that are not variables, for example the C string literal "Hello, world!". The string is placed somewhere in memory and has an address, it is an object. But it has no name so it isn't a variable.
Note: If nothing uses the address of an object the compiler may, and often will, optimize. Often the data is only kept in CPU registers and never actually stored in memory.
So to summarize: All variables are objects but not all objects are variables.
Current Draft Standard basic.pre.6 "A variable is introduced by the declaration of a reference other than a non-static data member or of an object. The variable's name, if any, denotes the reference or object."
Related
The standard says
A variable is introduced by the declaration of an object. The variable's name denotes the object.
But what does this definition actually mean?
Does a variable give a name to an object, i.e. are variables just a naming mechanism for otherwise anonymous objects? Or is a variable the name itself?
Or is a variable a named object in the sense that every variable is also an object?
Or is a variable just a "proxy" with a name that "delegates" all operations to the real object?
To confuse things further, many C++ books seem to treat variables and objects as synonyms.
What is your take on this?
About entities, quoting from the C++0x draft:
An entity is a value, object, reference, function [...]
Every name that denotes an entity is introduced by a declaration.
A variable is introduced by the declaration of an object
From these statements I draw the conclusion that a variable is a name and thus cannot be an object. This is really confusing the hell out of me :)
Variables are named objects. The following create objects that are not variables
new int // create one int object
std::string() // create one string object
The following creates one array variable with name "foo" and 5 unnamed (sub-) objects of type "int"
int foo[5];
The following is not a variable in C++03, but has become a variable in C++0x (declared references are variables in C++0x, for details see the link)
extern int &r;
Does a variable give a name to an object, i.e. are variables just a naming mechanism for otherwise anonymous objects?
Variables are objects (or references respectively). The entity list (3/3 in C++03) of C++ contains multiple such is-a relationships. For instance, a sub-object is-a object and an array element is-a object and a class-member is-a object or function or type or template or enumerator.
The entity list of C++0x looks a bit cleaner to me, and it doesn't contain "variables", "instance of a function" (what that kind of entity even is has never been apparent to me), "sub-object" and "array element" anymore. Instead it added "template specialization" which either are functions, classes or templates (partial specializations).
The C++ object model at 1.8 says
An object can have a name (clause 3).
So if you like, you can formulate the statement as "The object's name denotes the object.".
Variables are names that you give to objects, so yes, objects are, by and large, anonymous.
Here's the definition from the C++17 standard:
A variable is introduced by the declaration of a reference other
than a non-static data member or of an object. The variable’s name, if
any, denotes the reference or object.
My take on this, quite frankly, is that that's not really a definition. It tells us what introduces a variable, but it doesn't define what a variable is.
Consider, for example:
int foo = 42;
This is a declaration of an object, so it "introduces" a variable. But what is the variable? Is the object named foo a variable? I would have thought so, but the definition doesn't actually say that. Apparently the "variable" has a name (in this case "foo") and that name denotes the object. Since it has a name, presumably the name itself is not the variable. And it would have been easy enough to say that the variable is the object, rather than that the variable's name denotes the object, if that were the intent.
What is a "variable" in C++? I really don't know, and I don't believe it's possible to answer the question based on the wording in the standard. (And I'd like that to be corrected in a future edition.)
(The C standard deals with this by not defining "variable" and, for the most part, not using it except as an adjective or informally.)
A variable is simply an entity with a type and a name
As I have learned
What are variables
A variable is an identifier that is bind to a value stored in the system's memory(imperative languages) or an expression that can be evaluated(functional languages).
Why we need variables
provide names for storage chunks to store data temporarily during the lifespan of a computer program.
are also used in programming to transfer information from one part of the program to another part(Eg: parameters, global variables).
A variable is really a name given to an object in memory and hence an object is an anonymous type in that respect just at the point before compilation, when the compilation occurs, the variable is kept track of during the syntactical and parsing phase, then when the linker kicks in, that variable will have a memory address assigned to it, although at run-time, that memory address will be correctly off-setted somewhere to take into account of dynamic linking or static linking. Hence the variable can then be easily referenced aka the memory address that the variable is assigned to.
Really, in a nutshell, the variable is to help the programmer to work out the junction points of execution where that variable is referenced in terms of machine code.
What is your take on this?
Variable is a block of memory on stack or in code segment, or a value in a register (if the size of variable is small enough, although normally it is still value in a memory while registers hold temporary results), with name provided for programmer's convenience. Name of variable does not exist after compilation (we're not talking about macro tricks here). Any access to the variable is resolved into memory access, so technically variable is an address of corresponding data block, and that address isn't stored anywhere. Think about declaration of variables in assembly languages - variable "kinda" exists, but it is still merely an offset to the data block.
I think that this definition is quite clear.
The variable is introduced by declaration and denotes the object. Who introduces the variable? You do of course, and thus it is you who uses it.
A variable is really only a convenience for you the developer. It is a fundamental aspect of most programming languages not just C++. A variable mearly gives a symbolic name to a useable entity that occupies storage, such that it can be referenced and used at a future point in your source code.
For example if you declare a variable in a method as such:
int x = 5;
This will be reduced by the compiler to some offset from the stack pointer, say SP + 0x003.
At some point later you can say:
x = 52;
In this case the area of stack memory SP + 0x003 will contain the bytes that describe the number 52.
You declare the variable to be of a certain type so that the compiler can work out how much space the data occupies in memory.
Without variables, you would have to manage all of the arrangement of information yourself and you would probably be coding in assembly or lower.
Variable is a name for the object. You access the object through this named entity.
[basic] p6 states:
A variable is introduced by the declaration of a reference other than a non-static data member or of an object. The variable's name, if any, denotes the reference or object.
int a = 0; // declaration of an object, this introduces the variable x, and an object is created
int{0}; // not a declaration of a variable, this does not introduce a variable, but an object is created
Does this mean that a variable IS an object or reference (that is not a non-static member)? Throughout the standard, they are referred to as if they have the properties of objects/reference, but the formal definition does not seem to state that. What confuses me is that the variables name refers to the object or reference, rather than the variable itself.
For example, here is what [basic.life] p1 has to say:
A variable is said to have vacuous initialization if it is default-initialized and [...]
This alludes to variables having the same properties as objects and references, as they can be initialized.
So my question is:
Are variables simply a syntactic construct meant to group object and references that have been introduced by a declaration into one term? Is the variable itself the object or reference?
As made clear in Basic/3, variables are not "entities". Objects and references are entities, but not variables. As such, you could consider variables to be purely syntactic constructs rather than first-class C++ things.
Basic/6 tells us that a variable name denotes the object/reference declared by that variable. This is supposed to be read as plain English: an object/reference created via a variable declaration has a variable name. And conversely, a variable names an object/reference created via a variable declaration.
So when the standard says:
A variable is said to have vacuous initialization if it is default-initialized and...
It means:
A [reference/object introduced by a variable declaration] is said to have vacuous initialization if it is default-initialized and...
In the c++ standard there following definition of an entity can be found:
[basic]/3 ( http://eel.is/c++draft/basic#3 ):
An entity is a value, object, reference, function, enumerator, type,
class member, bit-field, template, template specialization, namespace,
parameter pack, or this.
What is a value in this context?
Is there any rule of the standard using the term entity, where it would make a difference if we didn't consider a value an entity?
Is a pr-value expression a value?
The C++ language standard is infamously vague about formally defining what an "object" and a "value" is. There are efforts to improve this (e.g. N4430), but not before C++17.
At present, one of the definitions of "object" is "a region of storage". The term "value" is never defined; the taxonomy of lvalues and rvalues does not have "value" as its common ancestor, but rather "expression".
For the time being, I would like to offer the following commentary.
Every value is an object: every value has a type, and the type is an object type, which is the type of that object. Conversely, every object has a value. The distinction is in usage: when talking about an object, usually it is the storage of the entity that is under consideration, while values are the result of evaluation of an expression. The value of an object is obtained by evaluating the object, or more precisely by evaluating any expression whose value is that object (tautologically). In yet other words, values are the subjects of computation, and objects are the means by which values are stored.
The distinction comes into play when you consider rules that concern accessing an object through a value. Evaluating an id-expression that names an object yields an lvalue that is that object, and this is the canonical way of accessing that object. But you can produce other values and access the object that way:
unsigned char x;
x = 10; // "x" is an expression and an lvalue
reinterpret_cast<signed char &>(x) = 20; // access through a different lvalue
(Note incidentally that variables can, but need not be objects (they can also be references), but evaluating an id-expression that names a variable always produces a value, hence an object. Conversely, not all objects are variables (e.g. a new expression produces an object that is not a variable), but all object types can in principle be the type of a variable (subject to constructibility and destructibility).)
Values are more diverse than objects, too. Consider this simple example:
int a;
int b = 10;
b = a;
The last line contains two objects, but several values: b is an lvalue of type int that is the object of the variable b. The expression a on the RHS is also an lvalue of type int, being the object of the variable a. But this value is not suitable for assignment. First, there is an implicit conversion, an lvalue-to-rvalue conversion, which produces a new value. This value is still the same object, but it is a prvalue, and it is that value that is used in the evaluation of the assignment.
Finally, we have temporaries: Are they temporary values or temporary objects? Until recently the Standard was sly and just called them "temporaries", but recently this was made more precise in a few places and now says "temporary objects". Clearly for the purpose of evaluation it does not matter where the value is stored, and the fact that the storage and lifetime are temporary is what matters, so "temporary object" is appropriate. Note that even though you cannot take the address of a temporary object with the built-in address-of operator, such objects can of course have addresses (which can be exported e.g. via a class member function returning this). It's just not valid beyond the limited lifetime of the temporary object.
In a nutshell: Objects and values are different facets of the same thing, but viewed from different perspectives: respectively the perspectives of evaluation on one side and storage, access and lifetime on the other.
Parsing the chapter in the link, I read
Every name that denotes an entity is introduced by a declaration.
Apparently we can name values! (Are that consts? Edit: Apparently not, but template arguments can be named values, cf. comment by hvd below.). We can name only one thing which is not an entity, that is labels.
Could someone point me to the (official) definition of object in C++? In the current specification, the word "object" is used a few thousand of times, but I can't seem to find a section or reference that explains what an object is.
The background to this somehow basic question is a discussion I recently had with another user, who was surprised to my question of whether a pointer to a variable of a scoped enum type could be considered an object pointer.
According to what he says, in C++ each variable is an object, hence also the variable i in int i = 42;.
Anyway, I could find other sources stating that an object in C++ is an instance of a class (and this is surely what I was taught at school many years ago), which contradicts in my understanding the assumption above that any variable is an object. Or is there an explanation to this apparent contradiction?
References aren't objects. Instances of pretty much any other type are.
Here's the definition, found in section 1.8:
The constructs in a C ++ program create, destroy, refer to, access, and manipulate objects. An object is a region of storage. [ Note: A function is not an object, regardless of whether or not it occupies storage in the way that objects do. — end note ] An object is created by a definition (3.1), by a new-expression (5.3.4) or by the implementation (12.2) when needed. The properties of an object are determined when the object is created. An object can have a name (Clause 3). An object has a storage duration (3.7) which influences its lifetime (3.8). An object has a type (3.9). The term object type refers to the type with which the object is created. Some objects are polymorphic (10.3); the implementation generates information associated with each such object that makes it possible to determine that object's type during program execution. For other objects, the interpretation of the values found therein is determined by the type of the expressions (Clause 5) used to access them.
More useful is the definition of object type in 3.9p8:
An object type is a (possibly cv-qualified) type that is not a function type, not a reference type, and not a void type.
Functions have function type but they aren't instances, and there never are instances of void.
To deal with your particular debate, you need the definition of object pointer, from 3.9.2p3:
The type of a pointer to void or a pointer to an object type is called an object pointer type.
As it turns out, the definition of object never mattered, only the definition of object type. A pointer to a scoped enum is certainly an object pointer (and it is itself also an object).
You'll find that the Standard uses the phrase class object when it means to restrict to instances of class, struct, or union type.
The standard says
A variable is introduced by the declaration of an object. The variable's name denotes the object.
But what does this definition actually mean?
Does a variable give a name to an object, i.e. are variables just a naming mechanism for otherwise anonymous objects? Or is a variable the name itself?
Or is a variable a named object in the sense that every variable is also an object?
Or is a variable just a "proxy" with a name that "delegates" all operations to the real object?
To confuse things further, many C++ books seem to treat variables and objects as synonyms.
What is your take on this?
About entities, quoting from the C++0x draft:
An entity is a value, object, reference, function [...]
Every name that denotes an entity is introduced by a declaration.
A variable is introduced by the declaration of an object
From these statements I draw the conclusion that a variable is a name and thus cannot be an object. This is really confusing the hell out of me :)
Variables are named objects. The following create objects that are not variables
new int // create one int object
std::string() // create one string object
The following creates one array variable with name "foo" and 5 unnamed (sub-) objects of type "int"
int foo[5];
The following is not a variable in C++03, but has become a variable in C++0x (declared references are variables in C++0x, for details see the link)
extern int &r;
Does a variable give a name to an object, i.e. are variables just a naming mechanism for otherwise anonymous objects?
Variables are objects (or references respectively). The entity list (3/3 in C++03) of C++ contains multiple such is-a relationships. For instance, a sub-object is-a object and an array element is-a object and a class-member is-a object or function or type or template or enumerator.
The entity list of C++0x looks a bit cleaner to me, and it doesn't contain "variables", "instance of a function" (what that kind of entity even is has never been apparent to me), "sub-object" and "array element" anymore. Instead it added "template specialization" which either are functions, classes or templates (partial specializations).
The C++ object model at 1.8 says
An object can have a name (clause 3).
So if you like, you can formulate the statement as "The object's name denotes the object.".
Variables are names that you give to objects, so yes, objects are, by and large, anonymous.
Here's the definition from the C++17 standard:
A variable is introduced by the declaration of a reference other
than a non-static data member or of an object. The variable’s name, if
any, denotes the reference or object.
My take on this, quite frankly, is that that's not really a definition. It tells us what introduces a variable, but it doesn't define what a variable is.
Consider, for example:
int foo = 42;
This is a declaration of an object, so it "introduces" a variable. But what is the variable? Is the object named foo a variable? I would have thought so, but the definition doesn't actually say that. Apparently the "variable" has a name (in this case "foo") and that name denotes the object. Since it has a name, presumably the name itself is not the variable. And it would have been easy enough to say that the variable is the object, rather than that the variable's name denotes the object, if that were the intent.
What is a "variable" in C++? I really don't know, and I don't believe it's possible to answer the question based on the wording in the standard. (And I'd like that to be corrected in a future edition.)
(The C standard deals with this by not defining "variable" and, for the most part, not using it except as an adjective or informally.)
A variable is simply an entity with a type and a name
As I have learned
What are variables
A variable is an identifier that is bind to a value stored in the system's memory(imperative languages) or an expression that can be evaluated(functional languages).
Why we need variables
provide names for storage chunks to store data temporarily during the lifespan of a computer program.
are also used in programming to transfer information from one part of the program to another part(Eg: parameters, global variables).
A variable is really a name given to an object in memory and hence an object is an anonymous type in that respect just at the point before compilation, when the compilation occurs, the variable is kept track of during the syntactical and parsing phase, then when the linker kicks in, that variable will have a memory address assigned to it, although at run-time, that memory address will be correctly off-setted somewhere to take into account of dynamic linking or static linking. Hence the variable can then be easily referenced aka the memory address that the variable is assigned to.
Really, in a nutshell, the variable is to help the programmer to work out the junction points of execution where that variable is referenced in terms of machine code.
What is your take on this?
Variable is a block of memory on stack or in code segment, or a value in a register (if the size of variable is small enough, although normally it is still value in a memory while registers hold temporary results), with name provided for programmer's convenience. Name of variable does not exist after compilation (we're not talking about macro tricks here). Any access to the variable is resolved into memory access, so technically variable is an address of corresponding data block, and that address isn't stored anywhere. Think about declaration of variables in assembly languages - variable "kinda" exists, but it is still merely an offset to the data block.
I think that this definition is quite clear.
The variable is introduced by declaration and denotes the object. Who introduces the variable? You do of course, and thus it is you who uses it.
A variable is really only a convenience for you the developer. It is a fundamental aspect of most programming languages not just C++. A variable mearly gives a symbolic name to a useable entity that occupies storage, such that it can be referenced and used at a future point in your source code.
For example if you declare a variable in a method as such:
int x = 5;
This will be reduced by the compiler to some offset from the stack pointer, say SP + 0x003.
At some point later you can say:
x = 52;
In this case the area of stack memory SP + 0x003 will contain the bytes that describe the number 52.
You declare the variable to be of a certain type so that the compiler can work out how much space the data occupies in memory.
Without variables, you would have to manage all of the arrangement of information yourself and you would probably be coding in assembly or lower.
Variable is a name for the object. You access the object through this named entity.