Pergunta

Tenho um código desenvolvido em python 2.4++ e pode apostar, eu tenho que adaptar ele para python 2.1!

função decoradores foram tão atraente que eu usei @classmethod em alguns pontos, sem tomando conhecimento do fato de que ele só está disponível a partir da versão 2.4.a mesma funcionalidade é oferecida pela função de modificadores, mas estes apareceu em python 2.2.cfr: http://www.python.org/dev/peps/pep-0318/

agora alguns de nossos clientes parecem ser ainda depende de python 2.1 (ArcGIS 9.1 acompanha-lo e torna-lo não atualizável), onde nem mesmo a função de modificadores estão disponíveis...

Eu estava procurando alguns função de modificador de definições em python 2.1, mas eu não encontrei nenhum (quero dizer:de trabalho).qualquer pessoa com êxito para resolver este problema?

para ser mais concreto, eu preciso de uma maneira de executar essa 2.4 código em python 2.1:

Python 2.4.6 (#2, Mar 19 2009, 10:00:53) 
[GCC 4.3.3] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>> class sic:
...   def f(cls):
...     print cls.__name__
...   f = classmethod(f)
... 
>>> sic().f()
sic
>>> sic.f()
sic
>>> 
Foi útil?

Solução

Assim como na minha velha receita para 2.1 staticmethod:

class staticmethod:
    def __init__(self, thefunc): self.f = thefunc
    def __call__(self, *a, **k): return self.f(*a, **k)

você deve ser capaz de fazer um 2.1 classmethod como:

class classmethod:
    def __init__(self, thefunc): self.f = thefunc
    def __call__(self, obj, *a, **k): return self.f(obj.__class__, *a, **k)

Nenhum @-sintaxe de curso, mas, sim, a velha forma (como em 2.2):

class sic:
  def f(cls): ...
  f = classmethod(f)

Se isto não funcionar (desculpe, foi durante muitos anos desde que eu tinha um Python 2.1 volta para teste), a classe precisa ser fornecido de forma mais explícita-e desde que você chamar classmethod antes da classe de objeto existe, ele precisará ser por nome, assumindo uma classe global,

class classmethod2:
    def __init__(self, thefunc, clsnam):
        self.f = thefunc
        self.clsnam = clsnam
    def __call__(self, *a, **k):
        klass = globals()[self.clsnam]
        return self.f(klass, *a, **k)

class sic2:
  def f(cls): ...
  f = classmethod2(f, 'sic2')

É realmente difícil encontrar elegantes formas de obter o objeto de classe (suprimindo a necessidade de auto-é a parte fácil, e o que é suficiente para staticmethod:você só precisa quebrar a função em uma função não exigível) desde 2.1 só tinha herdado (velho estilo de classes), não utilizável metaclasses, e, portanto, nenhuma realmente boa forma de ter sic2.f() magicamente conseguir que o cls.

Uma vez que a falta de @ sintaxe em 2.1, inevitavelmente, requer a edição de código que usa @classmethod, uma alternativa é mover a funcionalidade (decorar alguns métodos para ser "classe") para a direita APÓS o final do class instrução (a vantagem é que o objeto de classe não existia naquela época).

class classmethod3:
    def __init__(self, thefunc, klass):
        self.f = thefunc
        self.klass = klass
    def __call__(self, *a, **k):
        return self.f(self.klass, *a, **k)

def decorate(klass, klassmethodnames):
  for n in klassmethodnames:
    thefunc = klass.__dict__[n]
    setattr(klass, n, classmethod3(thefunc, klass))

class sic2:
  def f(cls): ...
  def g(self): ...
  def h(cls): ...
decorate(sic2, ['f', 'h'])

Outras dicas

Se apenas o @classMethod precisar ser backupled para o Python 2.1.
Existe um Receita de emulação de classe de classe em python2.1
Espero que isso ajude.

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top