Message12456

Author jeff.allen
Recipients bmvanwyk, jeff.allen, tomluk, wfouche2, zyasoft
Date 2019-04-26.22:10:20
SpamBayes Score -1.0
Marked as misclassified Yes
Message-id <1556316620.57.0.813898768545.issue2445@roundup.psfhosted.org>
In-reply-to
Content
I wrote a diagnostic that finds all methods with conflicting definitions in a set of bases, and applied it to the bases in PyJavaType.init, just before we compute the MRO. Taking the example of a List type and method __eq__, we find a conflict but that the definition added to java.util.List wins:

>>> import java
>>> AL = java.util.ArrayList
java.util.AbstractList.__eq__ defined by:
  <type 'java.util.List'> as <method '__eq__' of 'java.util.List' objects>
  <type 'java.util.AbstractCollection'> as <method '__eq__' of 'java.lang.Object' objects>

The first base in the list is the one where __eq__ was found in .modified, and the others are those bases that disagree with it. The actual order of bases has te super-class last:
>>> AL.__bases__
(<type 'java.util.RandomAccess'>, <type 'java.lang.Cloneable'>, <type 'java.io.Serializable'>, <type 'java.util.AbstractList'>)
>>> AL.__mro__
(<type 'java.util.ArrayList'>, <type 'java.util.RandomAccess'>, <type 'java.lang.Cloneable'>, <type 'java.io.Serializable'>, <type 'java.util.AbstractList'>, <type 'java.util.List'>, <type 'java.util.AbstractCollection'>, <type 'java.util.Collection'>, <type 'java.lang.Iterable'>, <type 'java.lang.Object'>, <type 'object'>)
>>> AL.__eq__
<method '__eq__' of 'java.util.List' objects>


If we put the order of bases back to its earlier Java-like order (super-class then interfaces), and run this again, we see the expected change in __bases__ and consequences in the MRO:
>>> AL.__bases__
(<type 'java.util.AbstractList'>, <type 'java.util.RandomAccess'>, <type 'java.lang.Cloneable'>, <type 'java.io.Serializable'>)
>>> AL.__mro__
(<type 'java.util.ArrayList'>, <type 'java.util.AbstractList'>, <type 'java.util.AbstractCollection'>, <type 'java.util.List'>, <type 'java.util.Collection'>, <type 'java.lang.Iterable'>, <type 'java.util.RandomAccess'>, <type 'java.lang.Cloneable'>, <type 'java.io.Serializable'>, <type 'java.lang.Object'>, <type 'object'>)

However, the effective definition of __eq__ is still the one added to the proxy of List:
>>> AL.__eq__
<method '__eq__' of 'java.util.List' objects>

The exciting change is that we no longer fail the MQQueue import. :)
PS> dist\bin\jython -S -c "from org.python.tests.mro import IBMMQChallengeMRO as m; t=m.mq.jms.MQQueue"

However, we get an apparent regression in the handling of diamond inheritance of Map and Iterable (#1878) in test_java_integration. This regression may not be real: the test looks for a specific MRO, and of course the MRO has changed, but the essence of #1878 is that when a Map defines an __iter__ the operative definition should still come from (our proxy for) Iterable. And it does:

PS> dist\bin\jython -S -i -c "from javatests import DiamondIterableMapMRO"
>>> DiamondIterableMapMRO.__iter__
<method '__iter__' of 'java.lang.Iterable' objects>

The import of DiamondIterableMapMRO makes plenty of visits to handleMroError (on behalf of the class and its ancestors) since C3 stalls on the Java-like heterarchy. With the diagnostic turned on we can see the potential conflict over __iter__:
javatests.DiamondIterableMapMRO.__iter__ defined by:
  <type 'java.util.Map'> as <method '__iter__' of 'java.util.Map' objects>
  <type 'javatests.IPersistentMap'> as <method '__iter__' of 'java.lang.Iterable' objects>

However, the final MRO is such that <method '__iter__' of 'java.lang.Iterable' objects> wins:
>>> DiamondIterableMapMRO.__mro__
(<type 'javatests.DiamondIterableMapMRO'>, <type 'javatests.AFn'>, <type 'javatests.IFn'>, <type 'java.util.concurrent.Callable'>, <type 'java.lang.Runnable'>, <type 'javatests.ILookup'>, <type 'javatests.IPersistentMap'>, <type 'java.lang.Iterable'>, <type 'javatests.Associative'>, <type 'javatests.IPersistentCollection'>, <type 'javatests.Seqable'>, <type 'javatests.Counted'>, <type 'java.util.Map'>, <type 'java.lang.Object'>, <type 'object'>)

This makes me think that test_diamond_inheritance_of_iterable_and_map should not be testing for an exact MRO, only that Iterable precedes Map.
History
Date User Action Args
2019-04-26 22:10:20jeff.allensetmessageid: <1556316620.57.0.813898768545.issue2445@roundup.psfhosted.org>
2019-04-26 22:10:20jeff.allensetrecipients: + jeff.allen, zyasoft, tomluk, bmvanwyk, wfouche2
2019-04-26 22:10:20jeff.allenlinkissue2445 messages
2019-04-26 22:10:20jeff.allencreate