New submission from Dutcho <dut...@ziggo.nl>:

While `Flag() in Flag()` and `Flag() | Flag()` result in the expected outcomes, 
e.g. `str() in Flag()` unexpectedly returns `True`, whereas `Flag() | str()` as 
expected raises a TypeError.
    >>> import enum
    >>> ABC = enum.Flag('ABC', 'a, b, c')
    >>> ac = ABC.a | ABC.c
    >>> def test():
    ...     for x in (*ABC, 'test'):
    ...         print(x, end=' ')
    ...         try:
    ...             print(x in ac, end=' ')
    ...         except TypeError as e:
    ...             print(e, end=' ')
    ...         try:
    ...             print(x | ac)
    ...         except TypeError as e:
    ...             print(e)
    >>> test()
    ABC.a True ABC.c|a
    ABC.b False ABC.c|b|a
    ABC.c True ABC.c|a
    test True unsupported operand type(s) for |: 'str' and 'ABC'

Likely cause is modelling of Flag.__contains__ after Flag.__and__ etc., which 
is incorrect as __contains__ doesn't have a reflected version like __and__ etc. 
have. The returned `NotImplemented` is therefore not handled by the 
interpreter, although it is converted to bool to satisfy __contains__ return 
type.

This can be fixed by redefinition of Flag.__contains__ to raise TypeError:
    >>> def __contains__(self, other):
    ...     if not isinstance(other, self.__class__):
    ...         raise TypeError(f"unsupported operand type(s) for 'in': "
    ...                         f"{type(other).__qualname__!r} and 
{type(self).__qualname__!r}")
    ...     return other & self == other
    >>> enum.Flag.__contains__ = __contains__
    >>> test()
    ABC.a True ABC.c|a
    ABC.b False ABC.c|b|a
    ABC.c True ABC.c|a
    test unsupported operand type(s) for 'in': 'str' and 'ABC' unsupported 
operand type(s) for |: 'str' and 'ABC'

----------
components: Library (Lib)
messages: 314890
nosy: Dutcho
priority: normal
severity: normal
status: open
title: x in enum.Flag() is True when x is no Flag
type: behavior
versions: Python 3.6

_______________________________________
Python tracker <rep...@bugs.python.org>
<https://bugs.python.org/issue33217>
_______________________________________
_______________________________________________
Python-bugs-list mailing list
Unsubscribe: 
https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com

Reply via email to