问题
In the c++ standard, in [basic.lval]/11.6 says:
If a program attempts to access the stored value of an object through a glvalue of other than one of the following types the behavior is undefined:[...]
- an aggregate or union type that includes one of the aforementioned types among its elements or non-static data members (including, recursively, an element or non-static data member of a subaggregate or contained union),[...]
This sentence is part of the strict-aliasing rule.
Does it allow us to alias through class member access?
class A{ //"casted to" aggregate
int i;
float g;
};
int j=10;
int l = reinterpret_cast<A*>(&j)->i;
According to the standard, an object value is only accessed if the object is subject to lvalue-to-rvalue-conversion [conv.lval]/2.
[expr.ref] does not stipulate that the object-expression must refer to an object of that type, only that the glvalue must have class type (the object-expression is the expression at the left of the dot "."). Nevertheless there is a word that recurrently appears in sentence related to member access which may imply constraint on the program that I overlooked. For example [expr.ref]/4.1:
If E2 is a static data member and the type of E2 is T, then E1.E2 is an lvalue; the expression designates the named member of the class.
Could "designates" means that this member is within its lifetime and that I cannot use class member access to perfom aliasing? Or is it allowed by [basic.lval]/11.6?
回答1:
For non-static data member, the word is:
If E2 is a non-static data member and the type of E1 is “cq1 vq1 X”, and the type of E2 is “cq2 vq2 T”, the expression designates the named member of the object designated by the first expression.
Clearly the object designated by *reinterpret_cast<A*>(&j)
, i.e. j
, has no member, so the behavior is undefined by omission.
回答2:
Edit: After a long conversation with people who know better than me the conclusion is: it's "behaviour".
But who cares? It's terrible practice either way.
来源:https://stackoverflow.com/questions/53151521/could-we-access-member-of-a-non-existing-class-type-object