Edit detail for InstanceTridDynamicky revision 1 of 1

1
Editor: 127.0.0.1
Time: 2005/05/25 15:34:31 GMT+0
Note: oprava překlepu (pepr)

changed:
-
Dotaz

  - Chci dynamicky vytvářet instance tříd. 
  
  - Jsem začátečník, snažil jsem se vytvořit funkci, která by dynamicky vytvářela
  instance třídy.


Jedna odpověď

  V Pythonu se instance objektů vždy vytvářejí
  dynamicky. Využití funkce pro vytváření
  instancí má smysl pouze tehdy, když funkce na
  základě dalších okolností rozhodne, jaká instance
  (jaké třídy nebo s jakým vnitřním stavem). Pak
  se tomu říká "class factory". V tomto případě
  se funkce použije čistým způsobem (nevolá se s cílem
  využít vedlejší efekt, ale vracenou hodnotu).
  Použití by vypadalo nějak takto::
  
    class Trida1: 
        def __str__(self):
            return 'instance tridy Trida1'
    
    class Trida2: 
        def __str__(self):
            return 'instance tridy Trida2'
    
    
    def mojeClassFactory(okolnosti):
       if okolnosti == 7:
           return Trida1()
       elif okolnosti == 8:
           return Trida2()
       else:
           return None
    
    
    objA = mojeClassFactory(7)
    print 'objA:', objA
    
    objB = mojeClassFactory(8)
    print 'objB:', objB
    
    objC = mojeClassFactory(1)
    print 'objC:', objC
  
(Okolnosti mohou samozřejmě nabývat různou podobu.)



Druhá odpověď

  Následující příklad ukazuje princip::
  
    class MyClass:
    
        def __init__(self, a, b, c):
            self.a = a
            self.b = b
            self.c = c
    
        def __str__(self):
            return str(self.a) + ' ' + str(self.b) + ' ' + str(self.c)
    
    
    class OtherClass:
    
        def __init__(self, a):
            self.a = a
    
        def __str__(self):
            return 'OtherClass instance: ' + str(self.a)
    
    
    
    def createInstance(clsname, *args):
        try:
            cls = globals()[clsname]
            obj = cls(*args)
            return obj
        except:
            print 'Unknown class: ', clsname
            return None
    
    
    #-----------------------------------------------------
    
    o1 = MyClass(1, 2, 3)
    print o1
    
    o2 = createInstance('MyClass', *('a', 'b', 'c'))
    print o2
    
    o3 = createInstance('OtherClass', *('x',))
    print o3
    
    o4 = createInstance('AnotherClass', *('x', 'y', 'z'))
    print o4
    
    o5 = eval('MyClass')(*(5, 6, 7))
    print o5
    
    o6 = eval('MyClass')(8, 9, 10)
    print o6
    
    cls = eval('MyClass')
    o7 = cls(11, 12, 13)
    print o7
    
    ===================================================
    Výstup:
    
    1 2 3
    a b c
    OtherClass instance: x
    Unknown class:  AnotherClass
    None
    5 6 7
    8 9 10
    11 12 13
    
Funkce createInstance() byla nadefinována od boku.
Hledá objekt definující požadovanou třídu v globálním 
slovníku -- viz globals(). Protože se obecně předpokládá
různý počet parametrů, používá speciálnější způsob
předávání parametrů sekvencí. 

Použití eval není tak průhledné, ale je jednodušší
a má další (neukázané) možnosti.

Princip spočívá v nalezení interního objektu, který
reprezentuje požadovanou třídu. Přiřazením tento
objekt spojím s mnou zadaným jménem (jako u ostatních
proměnných). Voláním vzniká instance třídy. Při volání
musím předat požadované parametry.

Naznačená funkce createInstance() kombinuje
jak hledání třídy (třída je reprezentována objektem),
tak předávání parametrů. Poslední příklady (o6, o7)
ukazují lidštější způsob předávání parametrů. 
Poslední příklad dělá přesně totéž, co o6. Rozdíl
spočívá jen v tom, že se objekt reprezentující třídu
nejdříve zapamatuje pod jménem cls.

Další odpovědi?

 patří sem....


Dotaz

  • Chci dynamicky vytvářet instance tříd.
  • Jsem začátečník, snažil jsem se vytvořit funkci, která by dynamicky vytvářela instance třídy.

Jedna odpověď

V Pythonu se instance objektů vždy vytvářejí dynamicky. Využití funkce pro vytváření instancí má smysl pouze tehdy, když funkce na základě dalších okolností rozhodne, jaká instance (jaké třídy nebo s jakým vnitřním stavem). Pak se tomu říká "class factory". V tomto případě se funkce použije čistým způsobem (nevolá se s cílem využít vedlejší efekt, ale vracenou hodnotu). Použití by vypadalo nějak takto:

    class Trida1: 
        def __str__(self):
            return 'instance tridy Trida1'

    class Trida2: 
        def __str__(self):
            return 'instance tridy Trida2'

    def mojeClassFactory(okolnosti):
       if okolnosti == 7:
           return Trida1()
       elif okolnosti == 8:
           return Trida2()
       else:
           return None

    objA = mojeClassFactory(7)
    print 'objA:', objA

    objB = mojeClassFactory(8)
    print 'objB:', objB

    objC = mojeClassFactory(1)
    print 'objC:', objC

(Okolnosti mohou samozřejmě nabývat různou podobu.)

Druhá odpověď

Následující příklad ukazuje princip:

    class MyClass:

        def __init__(self, a, b, c):
            self.a = a
            self.b = b
            self.c = c

        def __str__(self):
            return str(self.a) + ' ' + str(self.b) + ' ' + str(self.c)

    class OtherClass:

        def __init__(self, a):
            self.a = a

        def __str__(self):
            return 'OtherClass instance: ' + str(self.a)

    def createInstance(clsname, *args):
        try:
            cls = globals()[clsname]
            obj = cls(*args)
            return obj
        except:
            print 'Unknown class: ', clsname
            return None

    #-----------------------------------------------------

    o1 = MyClass(1, 2, 3)
    print o1

    o2 = createInstance('MyClass', *('a', 'b', 'c'))
    print o2

    o3 = createInstance('OtherClass', *('x',))
    print o3

    o4 = createInstance('AnotherClass', *('x', 'y', 'z'))
    print o4

    o5 = eval('MyClass')(*(5, 6, 7))
    print o5

    o6 = eval('MyClass')(8, 9, 10)
    print o6

    cls = eval('MyClass')
    o7 = cls(11, 12, 13)
    print o7

    ===================================================
    Výstup:

    1 2 3
    a b c
    OtherClass instance: x
    Unknown class:  AnotherClass
    None
    5 6 7
    8 9 10
    11 12 13

Funkce createInstance() byla nadefinována od boku. Hledá objekt definující požadovanou třídu v globálním slovníku -- viz globals(). Protože se obecně předpokládá různý počet parametrů, používá speciálnější způsob předávání parametrů sekvencí.

Použití eval není tak průhledné, ale je jednodušší a má další (neukázané) možnosti.

Princip spočívá v nalezení interního objektu, který reprezentuje požadovanou třídu. Přiřazením tento objekt spojím s mnou zadaným jménem (jako u ostatních proměnných). Voláním vzniká instance třídy. Při volání musím předat požadované parametry.

Naznačená funkce createInstance() kombinuje jak hledání třídy (třída je reprezentována objektem), tak předávání parametrů. Poslední příklady (o6, o7) ukazují lidštější způsob předávání parametrů. Poslední příklad dělá přesně totéž, co o6. Rozdíl spočívá jen v tom, že se objekt reprezentující třídu nejdříve zapamatuje pod jménem cls.

Další odpovědi?

patří sem....