Как определить имена столбцов, используя цикл for внутри класса (IsDescription)

Мы знаем, что если нам нужно определить имена столбцов таблицы с помощью pytables, мы можем сделать это следующим образом:

class Project(IsDescription):
    alpha = StringCol(20)
    beta  = StringCol(20) 
    gamma = StringCol(20)

где альфа, бета и гамма — желаемые имена столбцов таблицы. Но предположим, что я хотел бы использовать список «Список_имен_столбцов», который содержит имена столбцов следующим образом: СписокИмен_Столбцов[0] = альфа, СписокИмен_Столбцов[1] = бета, СписокИмен_Столбцов[2] = гамма

Тогда как мне определить вышеуказанный класс «Проект»?

Я пробовал со следующим:

ColumnNames_list = []
ColumnNames_list[0] = alpha 
ColumnNames_list[1] = beta 
ColumnNames_list[2] = gamma

class Project(IsDescription):
    for i in range (0, 10):
        ColumnNames_list[i] = StringCol(20)  

Он показывает ошибку:

TypeError: передача неверного значения в столбец таблицы. Ожидал экземпляр Col (или подкласса) и получил: "2". Пожалуйста, используйте конструктор Col() или конструктор-потомок для правильной инициализации столбцов.


person Zaman    schedule 01.02.2015    source источник


Ответы (1)


Есть несколько вариантов. Первый (самый простой) — добавить атрибуты после создания класса:

class Project(IsDescription):
    pass

for name in ColumnNames_List:
    setattr(Project, name, StringCol(20))

Есть много разных подходов к этому (например, вы можете сделать это через декоратор класса).

Следующий вариант — использовать встроенный type для создания класса:

names = {name: StringCol(20) for name in ColumnNames_List}
Project = type('Project', (IsDescription,), names)

Преимущество этого подхода в том, что он по-прежнему работает, даже если какой-то странный метакласс на IsDescription требует установки атрибутов во время создания класса1. Пока мы говорим о метаклассах... вы можете использовать для этого метаклассы, но это почти наверняка излишне.

1Это редкое явление, но несколько популярных сторонних библиотек (например, sqlalchemy) используют метаклассы таким образом.

person mgilson    schedule 01.02.2015
comment
Потрясающий! Спасибо брат! Ваше второе решение сработало отлично! Приятной жизни! - person Zaman; 01.02.2015