You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

SQLAlchemy中如何将布尔列转为整数计算平均值?

解决SQLAlchemy中布尔类型转整数求平均的问题

这个问题我之前也碰到过,SQLAlchemy里直接对布尔字段用func.avg()会报错,因为它没法直接把布尔值当成数值来计算。下面是几种等价于PostgreSQL中::INT类型转换的实现方式:

方法1:使用Column的cast()方法(最简洁)

SQLAlchemy的字段对象本身提供了cast()方法,可以直接将布尔类型转为整数,写法非常直观:

from sqlalchemy import Integer, func
from your_module import Table  # 替换成你的表模型

# 构建查询
query = session.query(
    Table.id,
    func.avg(Table.cond.cast(Integer)).label('avg_cond')
).group_by(Table.id)

# 执行查询获取结果
results = query.all()

这里Table.cond.cast(Integer)就等价于PostgreSQL里的cond::INT,把布尔值true转成1,false转成0,之后再求平均就没问题了。

方法2:使用通用的func.cast()函数

如果需要更通用的写法(比如兼容其他数据库),可以用SQLAlchemy的func.cast()函数,效果和上面一样:

from sqlalchemy import Integer, func
from your_module import Table

query = session.query(
    Table.id,
    func.avg(func.cast(Table.cond, Integer)).label('avg_cond')
).group_by(Table.id)

方法3:用case表达式手动映射(最通用,跨数据库)

如果要完全脱离数据库对布尔类型的依赖,还可以用case表达式手动把布尔值映射成1和0,这种写法在任何数据库里都能正常工作:

from sqlalchemy import case, func
from your_module import Table

query = session.query(
    Table.id,
    func.avg(
        case(
            [(Table.cond, 1)],
            else_=0
        )
    ).label('avg_cond')
).group_by(Table.id)

这个逻辑很直白:当cond为true时取1,否则取0,再对这些数值求平均,结果和前两种方法完全一致。

补充说明

你之前直接用orm_query(Table.id, func.avg(Table.cond))报错的原因是,SQLAlchemy会把布尔字段当成布尔类型处理,而avg()函数需要数值类型的输入,所以必须先完成类型转换或者值映射。

内容的提问来源于stack exchange,提问作者DeanLa

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.15 06:29:58