Re: [Python.NET] Inheriting from abstract .NET class

Denis Akhiyarov <[email protected]>
Newsgroups gmane.comp.python.dotnet
Message-ID <CALxxJLTixj0hd8kyBneFbo6XLX6ZKnQOabxTPPb64HNBhb71Bw@mail.gmail.com>
You are not a "Python n00b" based on metaclass usage!

My recommendation is to keep simple integration layer between CPython and
.NET, hence metaclasses were/are not supported.

But contributions are welcome! Although I expect this to be a tremendous
undertaking based on reviewing multiple sources.

Note that metaclass is a very different low-level concept from higher-level
abstract classes in .NET, hence direct mapping (e.g. `.register()` ) is not
feasible.

Thanks,
Denis

On Thu, Sep 22, 2016 at 10:04 AM, Henning Moeller <HMoeller-CMT0JBRjnaxWk0Htik3J/[email protected]>
wrote:

> Hello out there,
>
>
>
> I’m trying to inherit from an abstract .NET base class in Python (2.7).
> I’m a Python n00b but from what I understood…
>
>
>
> Here’s what I managed to do in Python only and which works fine:
>
>
>
> [File: room.py] -------
>
> import abc
>
>
>
> class Room(object):
>
>     def __init__(self, door):
>
>         self.door = door
>
>
>
>     def open(self):
>
>         self.door.open()
>
>
>
>     def close(self):
>
>         self.door.close()
>
>
>
>     def is_open(self):
>
>         return self.door.is_open()
>
>
>
> class Door(object):
>
>     __metaclass__ = abc.ABCMeta
>
>
>
>     def open(self):
>
>         if not self.is_open():
>
>             self.toggle()
>
>
>
>     def close(self):
>
>         if self.is_open():
>
>             self.toggle()
>
>
>
>     @abc.abstractmethod
>
>     def is_open(self):
>
>         pass
>
>
>
>     @abc.abstractmethod
>
>     def toggle(self):
>
>         pass
>
>
>
> class StringDoor(Door):
>
>     def __init__(self):
>
>         self.status = "closed"
>
>
>
>     def is_open(self):
>
>         return self.status == "open"
>
>
>
>     def toggle(self):
>
>         if self.status == "open":
>
>             self.status = "closed"
>
>         else:
>
>             self.status = "open"
>
>
>
> class BooleanDoor(Door):
>
>     def __init__(self):
>
>         self.status = True
>
>
>
>     def is_open(self):
>
>         return self.status
>
>
>
>     def toggle(self):
>
>         self.status = not (self.status)
>
>
>
> Door.register(StringDoor)
>
> Door.register(BooleanDoor)
>
> -------
>
>
>
> Now, all I did was to replace the abstract base class Door by a C#
> representation:
>
>
>
> [File: PythonAbstractBaseClass.dll] -------
>
> namespace PythonAbstractBaseClass
>
> {
>
>     public abstract class Door
>
>     {
>
>         public virtual void Open()
>
>         {
>
>             if (!IsOpen())
>
>                 Toggle();
>
>         }
>
>
>
>         public virtual void Close()
>
>         {
>
>             if (IsOpen())
>
>                 Toggle();
>
>         }
>
>
>
>         public abstract bool IsOpen();
>
>         public abstract void Toggle();
>
>     }
>
> }
>
> -------
>
>
>
> Removing Door from the Python part and importing it from the .NET assembly
> instead, I end up with this:
>
>
>
> [File: room2.py] -------
>
> import clr
>
> import abc
>
> from PythonAbstractBaseClass import Door
>
>
>
> class Room(object):
>
>     def __init__(self, door):
>
>         self.door = door
>
>
>
>     def open(self):
>
>         self.door.open()
>
>
>
>     def close(self):
>
>         self.door.close()
>
>
>
>     def is_open(self):
>
>         return self.door.is_open()
>
>
>
> class StringDoor(Door):
>
>     def __init__(self):
>
>         self.status = "closed"
>
>
>
>     def is_open(self):
>
>         return self.status == "open"
>
>
>
>     def toggle(self):
>
>         if self.status == "open":
>
>             self.status = "closed"
>
>         else:
>
>             self.status = "open"
>
>
>
> class BooleanDoor(Door):
>
>     def __init__(self):
>
>         self.status = True
>
>
>
>     def is_open(self):
>
>         return self.status
>
>
>
>     def toggle(self):
>
>         self.status = not (self.status)
>
>
>
> Door.register(StringDoor)
>
> Door.register(BooleanDoor)
>
> -------
>
>
>
> But this fails with the following error message:
>
>
>
>     Door.register(StringDoor)
>
> AttributeError: type object 'Door' has no attribute 'register'
>
>
>
> From what I understood about abc.ABCMeta, this metaclass contributes the
> ‘register’ method. It seems that abstract C# classes do not come with the
> same metaclass. They instead come with metaclass “CLR Metatype” which
> obviously does not provide ‘register’.
>
>
>
> But if I drop the call to ‘register’, on instantiating one of the derived
> classes, I receive the error message
>
>
>
>     sdoor = StringDoor()
>
> TypeError: cannot instantiate abstract class
>
>
>
> Is there a way to inherit from an abstract .NET class or is this is
> missing feature?
>
>
>
> Thanks in advance,
>
>
>
> Henning
>
>
>
> _________________________________________________
> Python.NET mailing list - [email protected]
> https://mail.python.org/mailman/listinfo/pythondotnet
>

_________________________________________________
Python.NET mailing list - [email protected]
https://mail.python.org/mailman/listinfo/pythondotnet
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.