def clip_root(self, term, order): left_bound = 1 if self.space.offset is not None: left_bound = self.space.offset+1 right_bound = left_bound+1 if self.space.limit is not None: right_bound = left_bound+self.space.limit term = OrderTerm(self.state.tag(), term, order, None, None, term.space, term.baseline, term.routes.copy()) term = PermanentTerm(self.state.tag(), term, term.space, term.baseline, term.routes.copy()) row_num_code = FormulaCode(RowNumSig(), coerce(IntegerDomain()), self.space.flow) right_bound_code = LiteralCode(right_bound, coerce(IntegerDomain()), self.space.flow) right_filter = FormulaCode(CompareSig('<'), coerce(BooleanDomain()), self.space.flow, lop=row_num_code, rop=right_bound_code) term = FilterTerm(self.state.tag(), term, right_filter, term.space, term.baseline, term.routes.copy()) routes = term.routes.copy() row_num_unit = ScalarUnit(row_num_code, self.space, self.space.flow) routes[row_num_unit] = term.tag term = PermanentTerm(self.state.tag(), term, term.space, term.baseline, routes) left_bound_code = LiteralCode(left_bound, coerce(IntegerDomain()), self.space.flow) left_filter = FormulaCode(CompareSig('>='), coerce(BooleanDomain()), self.space.flow, lop=row_num_unit, rop=left_bound_code) term = FilterTerm(self.state.tag(), term, left_filter, term.space, term.baseline, term.routes.copy()) return term
def __call__(self): if self.space.limit is None and self.space.offset is None: return super(OracleCompileOrdered, self).__call__() left_limit = None if self.space.offset is not None: left_limit = self.space.offset+1 right_limit = None if self.space.limit is not None: if self.space.offset is not None: right_limit = self.space.limit+self.space.offset+1 else: right_limit = self.space.limit+1 kid = self.state.compile(self.space.base, baseline=self.state.root) order = arrange(self.space) kid = self.state.inject(kid, [code for code, direction in order]) routes = kid.routes.copy() for unit in spread(self.space): routes[unit] = routes[unit.clone(space=self.backbone)] kid = OrderTerm(self.state.tag(), kid, order, None, None, self.space, kid.baseline, routes) kid = PermanentTerm(self.state.tag(), kid, kid.space, kid.baseline, kid.routes.copy()) row_num_code = FormulaCode(RowNumSig(), coerce(IntegerDomain()), self.space.flow) if right_limit is not None: right_limit_code = LiteralCode(right_limit, coerce(IntegerDomain()), self.space.flow) right_filter = FormulaCode(CompareSig('<'), coerce(BooleanDomain()), self.space.flow, lop=row_num_code, rop=right_limit_code) kid = FilterTerm(self.state.tag(), kid, right_filter, kid.space, kid.baseline, kid.routes.copy()) else: kid = WrapperTerm(self.state.tag(), kid, kid.space, kid.baseline, kid.routes.copy()) routes = kid.routes.copy() if left_limit is not None: row_num_unit = ScalarUnit(row_num_code, self.space.base, self.space.flow) routes[row_num_unit] = kid.tag kid = PermanentTerm(self.state.tag(), kid, kid.space, kid.baseline, routes) if left_limit is not None: left_limit_code = LiteralCode(left_limit, coerce(IntegerDomain()), self.space.flow) left_filter = FormulaCode(CompareSig('>='), coerce(BooleanDomain()), self.space.flow, lop=row_num_unit, rop=left_limit_code) kid = FilterTerm(self.state.tag(), kid, left_filter, kid.space, kid.baseline, kid.routes.copy()) return kid
def __call__(self): if self.space.offset is None: return super(MSSQLCompileOrdered, self).__call__() kid = self.state.compile(self.space.base, baseline=self.state.root) order = arrange(self.space) kid = self.state.inject(kid, [code for code, direction in order]) ops = [] for code, direction in order: op = FormulaCode(SortDirectionSig(direction=direction), code.domain, code.flow, base=code) ops.append(op) row_number_code = FormulaCode(RowNumberSig(), coerce(IntegerDomain()), self.space.flow, partition=[], order=ops) row_number_unit = ScalarUnit(row_number_code, self.space.base, self.space.flow) tag = self.state.tag() routes = kid.routes.copy() routes[row_number_unit] = tag kid = PermanentTerm(tag, kid, kid.space, kid.baseline, routes) left_limit = self.space.offset+1 right_limit = None if self.space.limit is not None: right_limit = self.space.limit+self.space.offset+1 left_limit_code = LiteralCode(left_limit, coerce(IntegerDomain()), self.space.flow) right_limit_code = None if right_limit is not None: right_limit_code = LiteralCode(right_limit, coerce(IntegerDomain()), self.space.flow) left_filter = FormulaCode(CompareSig('>='), coerce(BooleanDomain()), self.space.flow, lop=row_number_unit, rop=left_limit_code) right_filter = None if right_limit_code is not None: right_filter = FormulaCode(CompareSig('<'), coerce(BooleanDomain()), self.space.flow, lop=row_number_unit, rop=right_limit_code) filter = left_filter if right_filter is not None: filter = FormulaCode(AndSig(), coerce(BooleanDomain()), self.space.flow, ops=[left_filter, right_filter]) routes = kid.routes.copy() for unit in spread(self.space): routes[unit] = routes[unit.clone(space=self.backbone)] return FilterTerm(self.state.tag(), kid, filter, self.space, kid.baseline, routes)
def clip(self, term, order, partition): prefix = "!htsql:%s" % term.tag row_number = FormulaCode(UserVariableSig("%s:row_number" % prefix), coerce(IntegerDomain()), self.space.flow) keys = [] for idx, code in enumerate(partition): key = FormulaCode( UserVariableSig("%s:partition:%s" % (prefix, idx + 1)), code.domain, self.space.flow) keys.append(key) #term = PermanentTerm(self.state.tag(), term, # term.space, term.baseline, term.routes.copy()) zero_term = ScalarTerm(self.state.tag(), self.state.root, self.state.root, {}) zero_units = [] code = FormulaCode(UserVariableAssignmentSig(), row_number.domain, self.space.flow, lop=row_number, rop=LiteralCode(None, row_number.domain, self.space.flow)) unit = ScalarUnit(code, self.state.root, code.flow) zero_units.append(unit) for key in keys: code = FormulaCode(UserVariableAssignmentSig(), key.domain, self.space.flow, lop=key, rop=LiteralCode(None, key.domain, self.space.flow)) unit = ScalarUnit(code, self.state.root, code.flow) zero_units.append(unit) tag = self.state.tag() routes = {} for unit in zero_units: routes[unit] = tag zero_term.routes = routes zero_term = PermanentTerm(tag, zero_term, zero_term.space, zero_term.baseline, routes) filters = [ FormulaCode(NoOpConditionSig(), coerce(BooleanDomain()), self.space.flow, op=unit) for unit in zero_units ] filter = FormulaCode(AndSig(), coerce(BooleanDomain()), self.space.flow, ops=filters) zero_term = FilterTerm(self.state.tag(), zero_term, filter, zero_term.space, zero_term.baseline, {}) term = JoinTerm(self.state.tag(), term, zero_term, [], False, False, term.space, term.baseline, term.routes.copy()) order = [(code, +1) for code in partition] + order term = OrderTerm(self.state.tag(), term, order, None, None, term.space, term.baseline, term.routes.copy()) term = PermanentTerm(self.state.tag(), term, term.space, term.baseline, term.routes) next_units = [] conditions = [] for lop, rop in zip(keys, partition): condition = FormulaCode(IsEqualSig(+1), coerce(BooleanDomain()), self.space.flow, lop=lop, rop=rop) conditions.append(condition) if len(conditions) == 1: [condition] = conditions else: condition = FormulaCode(AndSig(), coerce(BooleanDomain()), self.space.flow, ops=conditions) one_literal = LiteralCode(1, coerce(IntegerDomain()), self.space.flow) on_true = FormulaCode(AddSig(), coerce(IntegerDomain()), self.space.flow, lop=row_number, rop=one_literal) on_false = one_literal value = FormulaCode(IfSig(), row_number.domain, self.space.flow, condition=condition, on_true=on_true, on_false=on_false) code = FormulaCode(UserVariableAssignmentSig(), row_number.domain, self.space.flow, lop=row_number, rop=value) row_number_unit = ScalarUnit(code, term.space, code.flow) next_units.append(row_number_unit) for lop, rop in zip(keys, partition): code = FormulaCode(UserVariableAssignmentSig(), lop.domain, self.space.flow, lop=lop, rop=rop) unit = ScalarUnit(code, term.space, code.flow) next_units.append(unit) tag = self.state.tag() routes = term.routes.copy() for unit in next_units: routes[unit] = tag term = PermanentTerm(tag, term, term.space, term.baseline, routes) left_bound = 1 if self.space.offset is not None: left_bound = self.space.offset + 1 right_bound = left_bound + 1 if self.space.limit is not None: right_bound = left_bound + self.space.limit left_bound_code = LiteralCode(left_bound, coerce(IntegerDomain()), term.space.flow) right_bound_code = LiteralCode(right_bound, coerce(IntegerDomain()), term.space.flow) left_filter = FormulaCode(CompareSig('>='), coerce(BooleanDomain()), term.space.flow, lop=row_number_unit, rop=left_bound_code) right_filter = FormulaCode(CompareSig('<'), coerce(BooleanDomain()), term.space.flow, lop=row_number_unit, rop=right_bound_code) filters = [left_filter, right_filter] filters += [ FormulaCode(NoOpConditionSig(), coerce(BooleanDomain()), self.space.flow, op=unit) for unit in next_units ] filter = FormulaCode(AndSig(), coerce(BooleanDomain()), self.space.flow, ops=filters) term = FilterTerm(self.state.tag(), term, filter, term.space, term.baseline, term.routes) return term
def clip(self, term, order, partition): baseline = self.space.ground while not baseline.is_inflated: baseline = baseline.base kid = self.state.compile(self.space.seed, baseline=baseline) codes = [code for code, direction in order] codes += self.space.companions kid = self.state.inject(kid, codes) kid = WrapperTerm(self.state.tag(), kid, kid.space, kid.baseline, kid.routes.copy()) limit = self.space.limit if limit is None: limit = 1 offset = self.space.offset key = [] for code, direction in arrange(self.space.seed, with_strong=False): if all(self.space.base.spans(unit.space) for unit in code.units): continue key.append(code) assert key correlations = [] filters = [] for code in partition: correlations.append(code) lop = CorrelationCode(code) rop = code filter = FormulaCode(IsEqualSig(+1), coerce(BooleanDomain()), self.space.flow, lop=lop, rop=rop) filters.append(filter) if len(filters) == 0: filter = None elif len(filters) == 1: [filter] = filters else: filter = FormulaCode(AndSig(), coerce(BooleanDomain()), self.space.flow, ops=filters) if filter is not None: kid = FilterTerm(self.state.tag(), kid, filter, kid.space, kid.baseline, kid.routes.copy()) kid = OrderTerm(self.state.tag(), kid, order, limit, offset, kid.space, kid.baseline, kid.routes.copy()) kid = CorrelationTerm(self.state.tag(), kid, kid.space, kid.baseline, kid.routes.copy()) if len(key) == 1: lop = rop = key[0] rop = ScalarUnit(rop, kid.space, kid.space.flow) else: filters = [] for code in key: correlations.append(code) lop = CorrelationCode(code) rop = code filter = FormulaCode(IsEqualSig(+1), coerce(BooleanDomain()), self.space.flow, lop=lop, rop=rop) filters.append(filter) filter = FormulaCode(AndSig(), coerce(BooleanDomain()), self.space.flow, ops=filters) lop = LiteralCode(True, coerce(BooleanDomain()), self.space.flow) rop = ScalarUnit(filter, kid.space, kid.space.flow) routes = term.routes.copy() routes[rop] = kid.tag kid = EmbeddingTerm(self.state.tag(), term, kid, correlations, term.space, term.baseline, routes) filter = FormulaCode(IsAnySig(+1), coerce(BooleanDomain()), self.space.flow, lop=lop, rop=rop) return FilterTerm(self.state.tag(), kid, filter, kid.space, kid.baseline, term.routes.copy())