我有一个名为logs的表,它有一个日期时间字段。我想根据特定的日期格式选择日期和行数。
我如何使用SQLAlchemy做到这一点?
我不知道一个通用的SQLAlchemy答案。大多数数据库支持某种形式的日期格式,通常通过函数。SQLAlchemy支持通过SQLAlchemy.sql.func调用函数。因此,例如,在Postgres后端和表my_table(foo varchar(30),当时间戳时)上使用SQLAlchemi,我可能会做一些类似的事情
my_table = metadata.tables['my_table']
foo = my_table.c['foo']
the_date = func.date_trunc('month', my_table.c['when'])
stmt = select(foo, the_date).group_by(the_date)
engine.execute(stmt)
按截断为月份的日期分组。但请记住,在该示例中,date_trunc()是Postgres的datetime函数。其他数据库将有所不同。你没有提到underlyig数据库。如果有一种独立于数据库的方法,我从来没有找到过。在我的案例中,我运行生产和测试aginst-Postgres和单元测试aginst-SQLite,并在单元测试中使用SQLite用户定义的函数来模拟Postgres日期时间函数。
当您只按未格式化的日期时间列分组时,计数会产生相同的结果吗?如果是这样,您可以运行查询,然后使用Python日期的strftime()方法。即
query = select([logs.c.datetime, func.count(logs.c.datetime)]).group_by(logs.c.datetime)
results = session.execute(query).fetchall()
results = [(t[0].strftime("..."), t[1]) for t in results]
我不知道SQLAlchemy,所以我可能偏离了目标。然而,我认为你所需要的只是:
SELECT date_formatter(datetime_field, "format-specification") AS dt_field, COUNT(*)
FROM logs
GROUP BY date_formatter(datetime_field, "format-specification")
ORDER BY 1;
好吧,也许您不需要ORDERBY,也许重新指定日期表达式会更好。可能有其他选择,例如:
SELECT dt_field, COUNT(*)
FROM (SELECT date_formatter(datetime_field, "format-specification") AS dt_field
FROM logs) AS necessary
GROUP BY dt_field
ORDER BY dt_field;
等等。基本上,您可以格式化日期时间字段,然后对格式化后的值进行分组等操作。