Перечислите все классы, которые существуют в настоящее время - PullRequest
2 голосов
/ 17 декабря 2008

Я создаю простой API, который создает типизированные классы на основе данных JSON, в которых определено обязательное поле типа. Эта строка используется для определения нового типа, добавления полей в объект JSON, создания его экземпляра и заполнения полей в экземпляре.

Что я хочу сделать, так это разрешить возможность предопределения этих типов в любом приложении, использующем мой модуль. Это позволяет добавлять методы и другие специфичные для приложения атрибуты, отсутствующие в объекте JSON. Я хотел бы, чтобы мой модуль проверил, существует ли тип, и если он есть, используйте его вместо динамического создания типа. Он по-прежнему будет добавлять атрибуты из объекта JSON, но он будет перерабатывать существующий тип.

Мои данные JSON:

{
    "type": "Person",
    "firstName": "John",
    "lastName": "Smith",
    "address": {
        "streetAddress": "21 2nd Street",
        "city": "New York",
        "state": "NY",
        "postalCode": 10021
    },
    "phoneNumbers": [
        "212 555-1234",
        "646 555-4567"
    ]
}

Мой код на данный момент (предположим, что json_object на данный момент является диктом):

if not json_object.has_key('type'):
    raise TypeError('JSON stream is missing a "type" attribute.')

##### THIS IS WHERE I WANT TO CHECK IF THE TYPE BY THAT NAME EXISTS ALREADY ####
# create a type definition and add attributes to it
definition = type(json_object['type'], (object,), {})
for key in json_object.keys():
    setattr(definition, key, None)

# instantiate and populate a test object
tester = definition()
for key, value in json_object.iteritems():
    setattr(tester, key, value)

Ответы [ 3 ]

3 голосов
/ 17 декабря 2008

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

json_types = {}
def get_json_type(name):
  try:
    return json_types[name]
  except KeyError:
    json_types[name] = t = type(json_object['type'], (object,), {})
    # any further initialization of t here
    return t

definition = get_json_type(json_object['type'])
tester = definition()
# or: tester = get_json_type(json_object['type'])()

Если вы хотите, чтобы они были добавлены в пространство имен модуля, выполните

json_types = globals()

вместо.

1 голос
/ 17 декабря 2008

Вы можете использовать dir(), чтобы получить список всех имен всех объектов в текущей среде, и вы можете использовать globals(), чтобы получить словарь, отображающий эти имена в их значения. Таким образом, чтобы получить только список объектов, которые являются классами, вы можете сделать:

import types
listOfClasses = [cls for cls in globals().values() if type(cls) == types.ClassType]
0 голосов
/ 17 декабря 2008

Вы можете использовать dir():

Python 2.5.2 (r252:60911, Oct  5 2008, 19:29:17)
[GCC 4.3.2] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>> dir()
['__builtins__', '__doc__', '__name__']
>>> class Foo:
...     pass
...
>>> dir()
['Foo', '__builtins__', '__doc__', '__name__']
>>> type(eval('Foo'))
<type 'classobj'>
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...