Sqlalchemy:在字符串左侧和列右侧时使用PSQL的`~`运算符

2 投票
2 回答
1374 浏览
提问于 2025-04-17 17:37

我知道这个:

WHERE column ~ 'regexp'

这是 sqlalchemy 的内容:

where(column.op('~')('regexp'))

但是我该怎么创建这个呢?

WHERE 'string' ~ column

(这个正则表达式是存储在数据库里的)

2 个回答

0

一个不依赖于Sqlalchemy的解决办法是,在PostgreSQL的后台创建你自己的运算符,并且把操作数的顺序调换过来。这样你就可以做一些像下面这样的事情:

string ### ANY(ARRAY[regexp1, regexp2, ...])

这里的###就是你自己定义的运算符。(给它起个好名字可能会有点难。)

4

你需要创建一个 literal() 或者一个 bindparam()

from sqlalchemy.sql import expression

expression.literal('string').op('~')(column)
# or
expression.bindparam('text', 'string').op('~')(column)

literal() 基本上就是一个带有隐含名称的 bindparam();在上面的例子中,'text' 是在 SQL 语句中使用的参数名称(键),而 'string' 是你希望出现在运算符左边的文本。

bindparam() 给你更多的控制权,包括可以传入一个 可调用对象,而不是一个具体的值:

def value_function():
    return some_calculation_result()

expression.bindparam('calculated_value', callable_=value_function).op('~')(column)

这样 SQLAlchemy 在发送语句到数据库服务器时会调用 value_function()。如果你有一系列的值,也会使用 bindparam(),SQLAlchemy 会自动调整表达式,以便应用于序列中的每个值:

strings = ['string1', 'string2', ...]
expression.bindparam('one_or_more', strings).op('~')(column)
# executes `('string1' ~ column OR 'string2' ~ column OR ...)`

撰写回答