2013-10-24 6 views
-3

Я относительно новичок в Python и спрашиваю себя, можно ли создавать классы, где имена динамически создаются внутри функции?Как динамически создавать классы

Код:

def create_dummy_elements(): 
    rows = [A,B,C,D,E,F,G,H,I] 
    columns = [A,B,C,D,E,F,G,H,I] 

    for r in range (rows): 
     for c in range (columns): 
      ***** = element(1,1,1,False) 

Мой результат должен быть 81 объектами "элемент" класса с именем, как AA, AB, AC, AD, ... * является то, что я на самом деле прошу. ..

+0

Вы хотите создать файл python с этими классами в файле? или вы хотите создать разные экземпляры этого класса? – jramirez

+2

Было бы проще создать словарь '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' '' ' Затем, как только он настроен, вы можете сказать, например, 'elems ['AA']', чтобы получить элемент 'AA'. – atomicinf

+2

Ваш пример не иллюстрирует эту часть «создавать классы, имена которых динамически создаются внутри функции» – oleg

ответ

1

Вы можете сделать список этих объектов, но это не так, чтобы динамически создавать имена переменных.

Что-то вроде этого:

my_list_of_elements = [] 
for r in range (rows): 
    for c in range (columns): 
     my_list_of_elements.append(element(1,1,1,False)) 

Тогда вы можете получить доступ к ним по номеру индекса, например: my_list_of_elements[n]

или в соответствии с двумерную стиль для петель у вас есть:

my_list_of_elements = [] 
for r in range (rows): 
    temp = [] 
    for c in range (columns): 
     temp.append(element(1,1,1,False)) 
    my_list_of_elements.append(temp) 

, то вы можете сделать my_list_of_elements[i][j] для доступа к i-й строке и j-му столбцу.

Если вы предпочитаете индекс строки, словарь будет служить вам хорошо:

my_dict_of_elements = {} 
for r in range (rows): 
    for c in range (columns): 
     my_dict_of_elements["element"+(r*c+c)] = element(1,1,1,False) 

, который даст вам доступ как этот my_dict_of_elements["element0"], например.

Как уже отмечался в комментариях по atomicinf на этом посте, вы можете использовать globals() Dict, но, кажется, мы оба согласны есть лучшие практики.

+2

Ну, вы _can_ динамически создаете имена переменных (играя с' globals() 'dict), но на самом деле нет причин делать это когда-либо. – atomicinf

+0

Ой забыл об этом бизнесе, я исправлю свои формулировки, но я не думаю, что когда-нибудь буду рекомендовать это, когда вы сможете просто использовать структуру данных. –

1

Я думаю, что вы можете просто можете создать список, как предложил farmerjoe, но если вы действительно хотите добавить namespases к глобальным, вы можете сделать это, как

class element(object): 
    def __init__(self, *args): 
     self._args = args 
    def __repr__(self): 
     return ' '.join(map(str, self._args)) 


rows = ['A','B'] 
columns = ['A','B'] 

for r in rows: 
    for c in columns: 
     exec('%s%s = element(r,c,False)' % (r,c)) 

print AB 

выход будет

A B False 
+1

В этом смысле я чувствую, что обращаюсь с ручной гранатой к обезьяне :). Что думает сообщество о слишком зрелых ответах на вопросы новорожденного? – alko

+0

Вместо 'exec' вы можете просто использовать' globals() [r + c] = element (r, c, False) '. Или еще лучше создать ссылку на глобальные переменные (чтобы избежать повторного вызова его, например '_globals = globals()'), а затем использовать '_globals [r + c] = blah blah blah'. –

+0

здесь есть одна оговорка, попробуйте globals() [4] = 5 против exec ('4 = 5') – alko

0

Хотя возможно, чтобы динамически создавать классы и именованный экземпляр классов в Python, это делается, как правило, неодобрительно. Считается более «Pythonic» и элегантным для хранения коллекций таких вещей в контейнере какого-то типа, например, в списке или словаре, а затем при необходимости обращаться к ним по индексу или ключу. Вот как это можно применить к вашей проблеме:

class Element(object): 
    def __init__(self, name, a=None, b=None, c=None): 
     self.name, self.a, self.b, self.c = name, a, b, c 
    def __str__(self): 
     classname = self.__class__.__name__ 
     return('{classname}(' 
       'name={self.name}, b={self.a}, ' 
       'c={self.b}, d={self.c})'.format(classname=classname, 
               self=self)) 
board = {} # empty dictionary 
for row in 'ABCDEFGHI': 
    for col in 'ABCDEFGHI': 
     name = row+col 
     board[name] = Element(name) # assign a named Element instance 

# sample usage 
board['AB'].a = 42 
print board['AB'] # Element(name=AB, a=42, b=None, c=None) 
board['GD'].c = 'something' 
print board['GD'] # Element(name=GD, a=None, b=None, c=something) 

Примечание: Я не знаю, как назвать большинство атрибутов Element класса, так что я только с помощью a, b и c в выше иллюстрации.

Смежные вопросы