更新
SQLAlchemy 1.1 and newer support TABLESAMPLE
爲selectables。 FromClause
元件具有方法FromClause.tablesample()
(認爲Table
S)和sqlalchemy.tablesample()
功能可以與所有selectables一起使用,例如聲明性模型的類:
from sqlalchemy import tablesample, func
from sqlalchemy.orm import aliased
# Create an alias for A that uses SYSTEM sampling method (default)
a_sampled = aliased(A, tablesample(A, 2.5))
# Create an alias for A that uses BERNOULLI sampling method
a_bernoulli = aliased(A, tablesample(A, func.bernoulli(2.5)))
有一個在該tablesample(A, ...)
輕微不對稱,其中A
是一個聲明類,返回一個TableSample
from-clause,如果用作模型,則必須使用別名。否則,它的行爲如同FromClause
,例如,模型類下的Table
。
之前
似乎是在寫這篇的時候no discussion約TABLESAMPLE
支持。由於SQLAlchemy的非常extensible,這裏是一個非常簡單(讀:可能不適合所有情況的工作)執行TABLESAMPLE支持:
from sqlalchemy.ext.compiler import compiles
from sqlalchemy.sql import Alias, FromClause
from sqlalchemy.orm import aliased
class TableSample(Alias):
__visit_name__ = 'tablesample'
def __init__(self, selectable, argument=None, method=None,
seed=None):
super(TableSample, self).__init__(selectable)
self.method = method
self.argument = argument
self.seed = seed
def tablesample(element, argument=None, method=None, seed=None):
if isinstance(element, FromClause):
return TableSample(element, argument=argument, method=method, seed=seed)
else:
return aliased(element, TableSample(element.__table__,
argument=argument, method=method, seed=seed))
@compiles(TableSample)
def compile_tablesample(element, compiler, **kwargs):
s = "%s TABLESAMPLE %s(%s)" % (
compiler.visit_alias(element, **kwargs),
element.method or 'SYSTEM',
element.argument)
if element.seed:
s += " REPEATABLE (%s)" % compiler.process(element.seed, **kwargs)
return s
的argument
應該是暫時只是代表0之間的百分比浮動100,儘管PostgreSQL會接受任何實值表達式。另一方面,seed
被編譯,所以文字python值必須用literal()
等來包裝。
應該以類似的方式來aliased
:
a_sampled = tablesample(A, 2.5)
query = session.query(a_sampled).options(
subqueryload(a_sampled.rel1),
subqueryload(a_sampled.rel2)
).filter(a_sampled.id >= min_id, a_sampled.id < max_id, [...])
謝謝你寫的代碼示例了太多!我對一個指針很滿意,這只是超出了預期。 –