def as_simple_expr(self, context): cond = as_simple_expr(self.cond, context) # filter is stored as an unevaluated expression filter_expr = context.get('__filter__') if filter_expr is None: context['__filter__'] = self.cond else: context['__filter__'] = filter_expr & self.cond iftrue = as_simple_expr(self.iftrue, context) if filter_expr is None: context['__filter__'] = ~self.cond else: context['__filter__'] = filter_expr & ~self.cond iffalse = as_simple_expr(self.iffalse, context) # This is probably useless because the only situation I can think of # where it could matter is inside the "iffalse" part of a nested if() # and in that case the contextual filter is overwritten using the value # of the filter at the *start* of the if() (see above), so it works # regardless of what we do here. It should not hurt to be correct # though. context['__filter__'] = filter_expr return Where(cond, iftrue, iffalse)
def as_simple_expr(self, context): # This will effectively trigger evaluation of expressions arguments # which are not handled by numexpr functions such has all expressions # inheriting from EvaluableExpression (e.g, uniform()) and their result # will be stored as a temporary variables in the context. The subtlety # to remember is that if a CompoundExpression "duplicates" arguments # (such as Logit), those must be either duplicate-safe or # EvaluableExpression. For example, if numexpr someday supports random # generators, we will be in trouble if we use it as-is. This means we # cannot keep the "compiled" expression, because the "temporary # variables" would only have a value in the first period, when the # expr is "compiled". This would tick the balance in favor of keeping a # build_context method. args = [as_simple_expr(arg, context) for arg in self.args] kwargs = {name: as_simple_expr(arg, context) for name, arg in self.kwargs} expr = self.build_expr(*args, **kwargs) # We need this because self.build_expr returns an Expr which can # contain CompoundExpressions return expr.as_simple_expr(context)
def as_simple_expr(self, context): cond = as_simple_expr(self.cond, context) # filter is stored as an unevaluated expression filter_expr = context.get('__filter__') if filter_expr is None: context['__filter__'] = self.cond else: context['__filter__'] = filter_expr & self.cond iftrue = as_simple_expr(self.iftrue, context) if filter_expr is None: context['__filter__'] = ~self.cond else: context['__filter__'] = filter_expr & ~self.cond iffalse = as_simple_expr(self.iffalse, context) context['__filter__'] = None return Where(cond, iftrue, iffalse)
def as_simple_expr(self, context): cond = as_simple_expr(self.cond, context) # filter is stored as an unevaluated expression context_filter = context.filter_expr local_ctx = context.clone() if context_filter is None: local_ctx.filter_expr = self.cond else: # filter = filter and cond local_ctx.filter_expr = LogicalOp('&', context_filter, self.cond) iftrue = as_simple_expr(self.iftrue, local_ctx) if context_filter is None: local_ctx.filter_expr = UnaryOp('~', self.cond) else: # filter = filter and not cond local_ctx.filter_expr = LogicalOp('&', context_filter, UnaryOp('~', self.cond)) iffalse = as_simple_expr(self.iffalse, local_ctx) return Where(cond, iftrue, iffalse)
def as_simple_expr(self, context): # This will effectively trigger evaluation of expressions arguments # which are not handled by numexpr functions such has all expressions # inheriting from EvaluableExpression (e.g, uniform()) and their result # will be stored as a temporary variables in the context. The subtlety # to remember is that if a CompoundExpression "duplicates" arguments # (such as Logit), those must be either duplicate-safe or # EvaluableExpression. For example, if numexpr someday supports random # generators, we will be in trouble if we use it as-is. This means we # cannot keep the "compiled" expression, because the "temporary # variables" would only have a value in the first period, when the # expr is "compiled". This would tick the balance in favor of keeping a # build_context method. args = [as_simple_expr(arg, context) for arg in self.args] kwargs = { name: as_simple_expr(arg, context) for name, arg in self.kwargs } expr = self.build_expr(context, *args, **kwargs) # We need this because self.build_expr returns an Expr which can # contain CompoundExpressions return expr.as_simple_expr(context)
def as_simple_expr(self, context): args, kwargs = as_simple_expr((self.args, self.kwargs), context) return self.__class__(*args, **dict(kwargs))
def as_simple_expr(self, context): return self.__class__(as_simple_expr(self.expr, context))