Сохранить сравнение в переменной (или выполнить сравнение, если оно задано в виде строки) - PullRequest
0 голосов
/ 16 января 2011

Хотелось бы узнать, позволяет ли сверхмощный питон сохранять сравнение в переменной или, если нет, возможно ли вызвать / выполнить сравнение, если задано в виде строки ("==" или "! =")

Я хочу предоставить пользователям моей программы возможность сравнения в строке.

Например, допустим, у меня есть список ..." продуктов "ипользователь хочет выбрать продукты, производителем которых является "foo".Он мог бы ввести что-то вроде: Product.manufacturer == "foo" и, если пользователю нужны продукты, производитель которых не является "bar", он введет Product.manufacturer! = "Bar"

Если пользователь вводит эту строку в виде строки, я создаю дерево со структурой, подобной:

            !=
         /     \
manufacturer   bar

Я бы хотел, чтобы это сравнение выполнялось правильно, но яне знаю, как это сделать, если ! = является строкой.

Поле «Manufacturer» является свойством, поэтому я могу правильно получить его из Product Класс и сохранить его (как свойство) в листе, и хорошо ... "бар" это просто строка.Я хотел бы знать, могу ли я что-то похожее на то, что я делаю с «изготовителем»: хранение его с «вызываемой» (своего рода) вещью: свойство с компаратором: ! =

Я пробовал с "eval", и это может сработать, но сравнения будут фактически использоваться для запроса базы данных MySQL (с использованием sqlalchemy), и я немного обеспокоен безопасностью этого ...

Любая идея будет высоко оценена. Спасибо!

PS: Идея всего этого заключается в том, чтобы генерировать запрос sqlalchemy, поэтому, если пользователь вводит строку: Product.manufacturer! = "foo" || Product.manufacturer! = "bar"

... Моя древовидная вещь может генерировать следующее: sqlalchemy.or_ (Product.manufacturer! = "foo", Product.factory! = "bar")

Так как sqlalchemy.or_ может вызываться, я также могу сохранить его в одном из листьев ... Я вижу проблему только с "! ="

1 Ответ

2 голосов
/ 16 января 2011

Я не очень много использовал SQLAlchemy, но, наверное, он использует Перегрузка оператора Python для обработки этих сравнений.Если это правда, то вы можете использовать магические методы свойств.Например:

Product.manufacturer == 'bar' => Product.manufacturer.__eq__('bar')
Product.manufacturer != 'foo' => Product.manufacturer.__ne__('foo')

Вы должны иметь возможность сделать getattr для объекта свойства для соответствующего магического метода:

method_map = {'==': '__eq__', '!=': '__ne__'}
comparison = getattr(Product.manufacturer, method_map[op])   # Here, 'op' is the operator (!=)
sqlalchemy.or_(comparison('foo'), comparison('bar'))         # Equivalent to: Product.manufacturer != 'foo' || Product.manufacturer != 'bar'

Надеюсь, это поможет:)

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...