Importer sous-classe d'une classe de base en Python
J'ai une classe de base qui a une méthode qui crée une instance d'une sous-classe qui est appelée la même que la chaîne d'entrée.
Cela fonctionnait avant en mettant les sous-classes de la classe de base dans le même fichier, et de faire quelque chose comme globals()[name]
.
Maintenant, cependant, j'ai divisé les sous-classes dans d'autres fichiers. Ils ont chacun une import base
déclaration au top, donc je ne peux pas simplement importer les sous-classes dans ma classe de base ou il va y avoir une chaîne de la circulaire de l'importation.
Est-il une solution pour cela?
Dans base.py:
from basefactory import BaseFactory
class Base:
def __init__(self, arg1, arg2):
...
def resolve(self, element):
className = typing.getClassName(element)
return BaseFactory.getInstance(className, element, self)
Dans basefactory.py:
from file1 import *
from file2 import *
...
class BaseFactory:
@staticmethod
def getInstance(name, arg1, arg2):
subclass = globals()[name]
return subclass(arg1, arg2)
Dans file1.py:
from base import Base
class subclass1(Base):
def foo(self):
return self.arg1
Est resolve() pour déterminer le type de classe, et de renvoyer une nouvelle instance de lui-même?
Il retourne une instance d'une sous-classe de Base.
Ce qui sur le déplacement de résoudre dans l'usine de la classe, qui est responsable du retour de l'instance correcte?
Il retourne une instance d'une sous-classe de Base.
Ce qui sur le déplacement de résoudre dans l'usine de la classe, qui est responsable du retour de l'instance correcte?
OriginalL'auteur Kevin Li | 2011-11-30
Vous devez vous connecter pour publier un commentaire.
Vous pouvez déplacer le
import
déclaration qui est un échec de la méthode qui crée le sous-objet.Les modules importés sont mis en cache dans
sys.modules
, donc je ne m'attends pas à un impact significatif.Aussi, je dois faire quelque chose le long des lignes de
from package.filename import *
pour chaque fichier. Dans l'avenir, je voudrais rappeler à ajouter plus d'importations à chaque fois que j'ajoute un nouveau fichier. Est-il plus compact de la syntaxe pour l'importation de tous les membres de tous les modules d'un paquet?Vous pouvez le faire "importer le package", et ensuite faire référence à des objets du paquet.nom de fichier.member1, package.fichier2.member2, etc.
Depuis mon sous-classe de l'instance créateur est automatique (basé sur des chaînes de caractères), je ne sais pas dans quel fichier le sous-classe est en.
OriginalL'auteur jcollado
De ce que je comprends, vous avez:
Une solution serait de créer une fonction /classe pour la méthode de fabrique, et le mettre dans un fichier séparé à partir de la classe de base. Ce fichier peut importer tous les fichiers de la classe de base et les classes dérivées sans la référence circulaire.
Par exemple:
En fait, la meilleure méthode serait d'utiliser type:
type(name, bases, dict)
renvoie un nouvel objet de type. C'est essentiellement une forme dynamique de la déclaration de classe. Le nom de la chaîne est le nom de la classe et devient le__name__
attribut; les bases de tuple détaille les classes de base et devient le__bases__
attribut; et ladict
dictionnaire est l'espace de noms qui contient les définitions d'une classe de corps et devient le__dict__
attribut. Par exemple, les deux instructions suivantes de créer le même type d'objets:Pourquoi ne pas déplacer les résoudre dans un gérant de classe? Avoir un regard sur le domaine de la classe dans Fabrique de classe en Python. Je ne suis pas sûr si résoudre est nécessaire... vous pouvez obtenir le nom de la classe directement à partir de
self.__class__.__name__
, et l'utilisation de fonctions python commetype()
etisinstance()
pour vérifier si ils sont un type particulier.Consultez également:
Pouvez-vous utiliser une chaîne à instancier une classe en python?
Python ont un équivalent à la Classe Java.forName()?
from sub1 import *
,from sub2 import *
..., et chaque sous-classe nefrom base import *
, cela permettra de jeter un ImportError après avoir tenté d'importer sub2. En essayant d'attraper l'exception et passer cela signifie que toutes les autres importations seront ignorés.Sauf si vous mettez de l'usine de la classe dans son propre fichier.
Une autre solution pourrait être de garder un meilleur contrôle de votre sous-classes, et de créer un dict qui indique la correspondance entre la chaîne et de votre classe dérivée, et l'importation de chacun de vos 60 classes de base dans l'usine de la classe de manière explicite.
J'ai fait mes classe usine importations de tout, de chaque sous-classe (qui importe la classe de base). Pendant ce temps, ma classe de base, qui est dans un fichier séparé, les importations de l'usine de la classe. Cela résulte dans une circulaire de l'importation.
La classe de base n'a pas besoin de savoir à propos de l'usine de la classe. Vous pourriez peut-être poster du code sur la façon dont ils sont entrelacés?
OriginalL'auteur Adam Morris
Je ne sais pas si je vous comprends,
pourquoi prenez-vous les sous-classes de la classe, si vous en avez besoin à l'intérieur? Laisser ensuite à l'intérieur de la classe et, partout où vous en avez besoin, vous pouvez
from class import subclass
60 sous-classes!! quels sont-ils?
OriginalL'auteur juankysmith