Как элегантно проверить существование объекта/экземпляра/переменной и одновременно назначить его переменной, если она существует в python?
Я использую SQLAlchemy для заполнения базы данных, и часто мне нужно проверить, существует ли объект orm в базе данных перед обработкой. Это может быть нетрадиционный вопрос, но я часто встречал эту схему:
my_object = session.query(SomeObject).filter(some_fiter).first()
if my_object: # Mostly in databases...
# Juchee it exists
# process
else:
# It does not exist. :-(
my_object = SomeObject()
# process
То, что я мечтаю, было бы чем-то вроде:
if my_object = session.query(someObject).blabla.first():
# if my_object is None this scope is left alone
# if my_object is not None I can work with my_object here...
Я знаю, что этот синтаксис неверен, но я хотел объяснить, что я имею в виду под этим примером. Любой эквивалентный способ сделает меня счастливым.
Есть ли элегантный шаблон для Python для этого шаблона? Этот вопрос направлен не только на SQLAlchemy, но и на каждый эквивалентный сценарий.
Закрывая мои глаза, ударяя "Отправьте свой вопрос" и ожидая, когда умные люди и пифонисты наизусть, чтобы выследить меня, чтобы спросить что-то, возможно, нецелесообразно; -)
Ответы
Ответ 1
Вы хотите выполнить запрос Exist эффективным
(ret, ), = Session.query(exists().where(SomeObject.field==value))
Майк Байер объяснил это в своем блоге:
http://techspot.zzzeek.org/2008/09/09/selecting-booleans/
Вы можете использовать скаляр, если вы не хотите иметь кортеж в качестве результата:
ret = Session.query(exists().where(SomeObject.field==value)).scalar()
Ответ 2
Это было задано давно, но для будущих посетителей более кратким способом проверки является
if session.query(model).filter(some_filter).count():
# do stuff
Ответ 3
оберните его на функцию (бесстыдно украденную из django get_or_create, это не возвращает кортеж, хотя)
get_or_create(model, **kwargs):
try:
# basically check the obj from the db, this syntax might be wrong
object = session.query(model).filter(**kwargs).first()
return object
except DoesNotExistException: # or whatever error/exception it is on SQLA
object = model()
# do it here if you want to save the obj to the db
return object
что он. использовать его:
obj = get_or_create(SomeObject, filters)
измените **kwargs
на простой аргумент (например, some_filters), если вы хотите
попытайтесь обернуть то, что вы часто используете (оберните их в функции или классы)
Это только псевдокод, может быть синтаксическая ошибка.
EDIT: подчеркнуть
Ответ 4
Я знаю, что это не один шаг, но приемлемо ли это?
my_object = session.query(SomeObject).filter(some_filter).first()
if my_object is None:
my_object = SomeObject()
#process
Ответ 5
from sqlalchemy.orm.util import has_identity
my_object = session.query(SomeObject).get(id) or SomeObject()
# Processing...
# Check if the object exists in the database
if not has_identity(my_object):
session.add(my_object)
session.commit()
.get() можно заменить фильтром() + first() при необходимости
Ответ 6
if DBSession.query(ObjectType).filter(ObjectType.some_parametter == "This").first() is None:
Это эффективный один способ проверки наличия записи. Он эффективен, потому что он захватывает только первый объект, и он может быть на одной строке, потому что first() возвращает None, когда нет соответствующих записей. Надеюсь, это поможет!
Ответ 7
Некоторые хорошие предложения здесь. Как насчет использования исключения NoResultFound?
try:
existing = dbsession.query(SomeObject).filter_by(value=value).one()
return existing
except sqlalchemy.orm.exc.NoResultFound:
obj = SomeObject()
Ответ 8
Вы можете использовать это:
sth = session.query.filter_by().first()
if sth is None:
....
else:
....
Я тестировал его. Он хорошо работает.