compiler: desugar x != y into not x == y (fixes #974).

This commit is contained in:
whitequark 2018-04-20 12:18:58 +00:00
parent a4f1877085
commit b4e3c30d8c
1 changed files with 17 additions and 9 deletions

View File

@ -1478,7 +1478,7 @@ class ARTIQIRGenerator(algorithm.Visitor):
else: else:
assert False assert False
def polymorphic_compare_pair_inclusion(self, op, needle, haystack): def polymorphic_compare_pair_inclusion(self, needle, haystack):
if builtins.is_range(haystack.type): if builtins.is_range(haystack.type):
# Optimized range `in` operator # Optimized range `in` operator
start = self.append(ir.GetAttr(haystack, "start")) start = self.append(ir.GetAttr(haystack, "start"))
@ -1522,21 +1522,29 @@ class ARTIQIRGenerator(algorithm.Visitor):
else: else:
assert False assert False
if isinstance(op, ast.NotIn): return result
result = self.append(ir.Select(result,
def invert(self, value):
return self.append(ir.Select(value,
ir.Constant(False, builtins.TBool()), ir.Constant(False, builtins.TBool()),
ir.Constant(True, builtins.TBool()))) ir.Constant(True, builtins.TBool())))
return result
def polymorphic_compare_pair(self, op, lhs, rhs): def polymorphic_compare_pair(self, op, lhs, rhs):
if isinstance(op, (ast.Is, ast.IsNot)): if isinstance(op, (ast.Is, ast.IsNot)):
# The backend will handle equality of aggregates. # The backend will handle equality of aggregates.
return self.append(ir.Compare(op, lhs, rhs)) return self.append(ir.Compare(op, lhs, rhs))
elif isinstance(op, (ast.In, ast.NotIn)): elif isinstance(op, ast.In):
return self.polymorphic_compare_pair_inclusion(op, lhs, rhs) return self.polymorphic_compare_pair_inclusion(lhs, rhs)
else: # Eq, NotEq, Lt, LtE, Gt, GtE elif isinstance(op, ast.NotIn):
result = self.polymorphic_compare_pair_inclusion(lhs, rhs)
return self.invert(result)
elif isinstance(op, (ast.Eq, ast.Lt, ast.LtE, ast.Gt, ast.GtE)):
return self.polymorphic_compare_pair_order(op, lhs, rhs) return self.polymorphic_compare_pair_order(op, lhs, rhs)
elif isinstance(op, ast.NotEq):
result = self.polymorphic_compare_pair_order(ast.Eq(loc=op.loc), lhs, rhs)
return self.invert(result)
else:
assert False
def visit_CompareT(self, node): def visit_CompareT(self, node):
# Essentially a sequence of `and`s performed over results # Essentially a sequence of `and`s performed over results