Closed stefjoosten closed 4 years ago
CtxError.hs, line 153: mkCyclesInGensError
Turn function mkCyclesInGensError
into a warning.CtxError.hs, line 166: mkMultipleRootsError
Turn function mkMultipleRootsError
into a warning.P2A_Converters.hs, line 377
Instead of calling mkCyclesInGensError
, function mkTypology
yields one concept with multiple names.P2A_Converters.hs, line 391
Instead of calling mkMultipleRootsError
, function mkTypology
produces one new concept that is the union of its constituents, together with the ISA's between each constituent and the newly generated concept.A_Concept
(AbstractSyntaxTree.hs line 754
), which must accommodate multiple names. I would expect that P_Context
need not have multiple names because that is a concept at parse-time. The P2A converter must collect multiple P_Concept
s into one A_Concept
.So what to do with
aConcept2pConcept :: A_Concept -> P_Concept
?instance Named A_Concept
?instance Eq A_Concept
?instance Ord A_Concept
?Hi Han, good questions!
To start with, what to do with instance Named A_Concept
? As there may be multiple names, the function name
must pick one. For this purpose, the A_Concept
must not only store different names, but also the contexts that define those names. For choosing which name to print, I suggest names from the "current context" have a preference. For now, I just pick the head from a NonEmpty P_Concept
.
For the instances Eq A_Concept
and Ord A_Concept
we leave the code as-is because it hinges on the hash attribute. We do not rely on the concept's name for equality, so there is no impact here:
instance Ord A_Concept where
compare (PlainConcept{cpthash=v1}) (PlainConcept{cpthash=v2}) = compare v1 v2
compare ONE ONE = EQ
compare ONE (PlainConcept{}) = LT
compare (PlainConcept{}) ONE = GT
instance Eq A_Concept where
(==) a b = compare a b == EQ
Then what about aConcept2pConcept :: A_Concept -> P_Concept
. It will become
aConcept2pConcept :: A_Concept -> NEL.NonEmpty P_Concept
So it yields a nonempty list instead of a single P_Concept
.
Functions pCpt2aCpt :: P_Concept -> A_Concept
gets a different setup, because a number of P_Concept
s from different contexts can be assembled into one A_Concept
, after a cycle of concepts is detected.
Makes sense. I recognize this from the OWL ontology language.
“NOTE: If we wanted to "upgrade" an axiom of the form "A subClassOf B" to "A equivalentClass B" (meaning that the class extension of A is not just any subset, but in fact the same set as the class extension of B), we could add a second subClassOf axiom of the form (B subClassOf A), which by definition makes the two class extensions equivalent (and thus has the same meaning as "A equivalentClass B"). Such subClassOf "cycles" are explicitly allowed. As OWL is usable in a distributed environment, this can be a useful feature.” Source: https://www.w3.org/TR/owl-ref/#subClassOf-def
I have implemented a nice solution to this problem, and created pull request https://github.com/AmpersandTarski/Ampersand/pull/1055 for it. The idea is that in the P-structure we harvest all concepts that are equivalent, based on cycles in the CLASSIFY statements. All such concepts will be considered as a single concept in the A-structure. All relations that have any of these concepts as source of target will have that single concept as source/target in the a-structure.
Some choices I made in this implementation:
show
function of A_Concept. It now shows not only the name, but all aliases as well. This could have effect on error messages.Great! I like this solution because it is upwards compatible and it maintains the rule in the metamodel that (A ISA B) /\ (B ISA A) <=> (A=B)
. (Currently, this rule is true but empty)
We will get some details to look after, which may pop up as issues in the future:
ONE
. I see no reason why the user could not rename it. Whether that is wise or not is for the user to judge. That would mean we might lift that restriction in the future without many consequences.Aliassing of concept names now works and is merged into development.
Problem
Ampersand-v3.17.2 and earlier prohibit cyclic dependencies in Concepts. Also, it prohibits multiple root concepts in a typology. However, as a user, I might have reasons to allow synonyms. For instance when combining different contexts (from different offspring) into a new context.
Solution intent
We could simply allow cyclic dependencies. All concepts in a cycle represent the same set of atoms, so effectively this means they will be synonyms of each other.
In the same effort, we can allow multiple roots (see issue #898). Note that this differs from allowing cyclic dependencies. It fits well in the philosophy of allowing things that have a reasonable interpretation. Nevertheless, a warning is in place, because sometimes people define multiple roots by mistake. The way to get rid of the warning is to define a concept for the union of the roots as described in issue #898.