Closed eclipse-ocl-bot closed 2 hours ago
By Laurent Goubet on Oct 08, 2009 08:10
I fully agree with all suggestions made here in comment #1, except for the two "toString". I'd rather remove the '$' here :
def OclVoid::toString() : String = null\ def OclInvalid::toString() : String = invalid
There cannot be any confusion with Java's null : OCL cannot return it (well ... it does in the current implementation, that's another issue), so let's just use the common names. If I type "null" in the OCL console, and it returns me "$null$", I'll just get confused :).
By Alexander Igdalov on Oct 08, 2009 14:56
(In reply to comment #0)
But Alex wrote
- oclIsKindOf(), oclIsTypeOf() invoked on
null
must returninvalid
regardless of the operation argument (even if it is OclVoid or OclInvalid). This is done in accordance with the spec.I think
def OclVoid::oclIsKindOf(type : Classifier) : Boolean = if type = OclInvalid then invalid else true endif def OclVoid::oclIsTypeOf(type : Classifier) : Boolean = type = OclVoid
both of which are the inherited OclAny behaviour (well it would be if OclAny defined false as the return when the preducate for a true return is not satisfied.)
Ed, at first I wanted to define oclIsKindOf() and oclIsTypeOf() on null
just the way you did above. As you have mentioned, this behaviour is inherited from OclAny. But then I recalled that in Java null instanceof SomeType
returns false. This behaviour is very sensible - it lets users avoid checks when type-checking is accompanied with subsequent type-casting. This can be illustrated by the example at http://hanuska.blogspot.com/2006/08/tricky-instanceof-operator.html
To get aligned with Java (oclIsKindOf() is a synonym of 'instanceof' in OCL), we could redefine null.oclIsKindOf(SomeType) so that it would return false regardless of SomeType argument (well, if SomeType is OclVoid it is arguable). It contradicts the OclAny::oclIsKindOf() behaviour but is sensible and is aligned with Java. If we follow this approach we should redefine OclVoid::oclIsTypeOf() in the same manner. IOW, we would do something like:
def OclVoid::oclIsTypeOf(type : Classifier) : Boolean = false.
Very confusing, isn't it?
The considerations above made me feel that following the spec for OclVoid::oclIsKindOf() and OclVoid::oclIsTypeOf() (i.e. return invalid) is the least bad option.
(In reply to comment #1)
I fully agree with all suggestions made here in comment #1, except for the two "toString". I'd rather remove the '$' here :
def OclVoid::toString() : String = null
Did actually you mean
def OclVoid::toString() : String = 'null' ?
def OclInvalid::toString() : String = invalid
+1
By Alexander Igdalov on Oct 08, 2009 15:02
(In reply to comment #2)
To make myself clear:
def OclInvalid::toString() : String = invalid
+1
I mean that invalid.toString()
should return invalid (an instance of OclInvalid) not a string literal which value is 'invalid'.
By Ed Willink on Jan 18, 2010 11:49
I have just submitted an OMG resolution suggesting that all oclXXX have explicit and useful reflective semantics. This was motivated by observing that a variety of well-formedness rules currently use oclIsTypeOf(OclVoid) and oclIsTypeOf(OclInvalid) in ways that only make sense if there are explicit overloads such as:
def OclVoid::oclIsTypeOf(Classifier c) : Boolean = c = null
def OclInvalid::oclIsTypeOf(Classifier c) : Boolean = c = invalid
In the new model-driven evaluation these behaviours can be configured arbitrarily by the presence of a definition of an e.g. OclVoid::oclIsTypeOf(Classifier c) associated with an OclVoidOclIsTypeOfOperatuion class that provides the reqiusite evaluate overloads. So we can offer a suite of OCL.oclstdlib models, selectable via an Environment.setLibrary() method, corresponding to each different OCL 2.1, 2.3, 2.5, 2.0A, 2.0B etc that we feel included to support.
By Ed Willink on Feb 01, 2011 02:25
Evaluator follows OMG resolution.
By Ed Willink on May 27, 2011 02:25
Closing since fixed in mature code too.
By Ed Willink on May 27, 2011 06:40
Resolved for Indigo is 3.1.0 not 3.2.0.
| --- | --- | | Bugzilla Link | 291721 | | Status | CLOSED FIXED | | Importance | P3 normal | | Reported | Oct 08, 2009 06:25 EDT | | Modified | May 27, 2011 06:40 EDT | | Version | 1.3.0 | | Blocks | 318248 | | Reporter | Ed Willink |
Description
Bug 282882 identified the inadequacies of OclVoid and OclInvalid definitions and provided a significant renaming patch.
Bug 281849 was pretty much a duplicate.
These provoked the raising of OMG Issue 14197 with substantial revised text.
Bug 291623 got sidetracked by detailed null handling, which provoked me to suggest refining that resolution. Achim endorses the suggestion.
This thread is initially for discussion of Issue 14197 and then for implementing it.
Repeating Alex's comments that seem unarguable
invalid
must return\invalid
regardless of the operation argument (even if it is invalid). This\ is done in accordance with the spec.def OclInvalid::oclAsType(type : Classifier) : T = invalid\ def OclInvalid::oclIsKindOf(type : Classifier) : Boolean = invalid\ def OclInvalid::oclIsTypeOf(type : Classifier) : Boolean = invalid
3.\ null.oclAsType(OclInvalid) -- returns invalid\ null.oclAsType(SomeTypeNotOclInvalid) -- returns null // the only deviation
def OclVoid::oclAsType(type : Classifier) : T =\ if type = OclInvalid then invalid else null endif
But Alex wrote
null
must returninvalid
\ regardless of the operation argument (even if it is OclVoid or OclInvalid).\ This is done in accordance with the spec.I think
def OclVoid::oclIsKindOf(type : Classifier) : Boolean =\ if type = OclInvalid then invalid else true endif\ def OclVoid::oclIsTypeOf(type : Classifier) : Boolean =\ type = OclVoid
both of which are the inherited OclAny behaviour (well it would be if OclAny defined false as the return when the preducate for a true return is not satisfied.)
Also
null.oclIsInState(...) => false
def OclVoid::oclIsInState(statespec : OclState) : Boolean = false
Philosophically; null is an object that exists, has a type (conformant to all types except OclInvalid) but does not have a value. Therefore any type-based operation behaves like OclAny, any value-based operation needs consideration.
This suggests that
def OclVoid::toString() : String = ???
not sure how to spell null; perhaps $null$
and then does
def OclInvalid::toString() : String = $invalid$