Some code has been simplified, added docstring, bugs fixed and test added. --- sympy/queries/__init__.py | 15 ++++----------- sympy/queries/handlers/__init__.py | 4 +++- sympy/queries/handlers/calculus.py | 4 +++- sympy/queries/handlers/ntheory.py | 2 +- sympy/queries/handlers/order.py | 30 ++++++++++++++++++++++-------- sympy/queries/handlers/sets.py | 2 +- sympy/queries/tests/test_query.py | 5 +++++ 7 files changed, 39 insertions(+), 23 deletions(-)
diff --git a/sympy/queries/__init__.py b/sympy/queries/__init__.py index d8146fd..8954268 100644 --- a/sympy/queries/__init__.py +++ b/sympy/queries/__init__.py @@ -28,7 +28,7 @@ class Q: odd = 'odd' # TODO: maybe this should be moved to another file? -def ask(expr, key, assumptions=[]): +def ask(expr, key, assumptions=True): """ Method for inferring properties about objects. @@ -58,13 +58,7 @@ def ask(expr, key, assumptions=[]): the official release """ expr = sympify(expr) - - if assumptions: - assumptions = And(assumptions, And(*global_assumptions)) - elif global_assumptions: - assumptions = And(*global_assumptions) - if not isinstance(assumptions, (list, tuple)): - assumptions = conjuncts(to_cnf(assumptions)) + assumptions = And(assumptions, And(*global_assumptions)) # direct resolution method, no logic resolutors = [] @@ -82,8 +76,7 @@ def ask(expr, key, assumptions=[]): if res is not None: return res - if assumptions: pass - else: return + if assumptions is True: return # use logic inference if not expr.is_Atom: return @@ -91,8 +84,8 @@ def ask(expr, key, assumptions=[]): for k, values in known_facts_dict.iteritems(): for v in values: clauses.append(Equivalent(compile_rule(k), compile_rule(v))) - result = None + assumptions = conjuncts(to_cnf(assumptions)) # add assumptions to the knowledge base for assump in assumptions: conj = eliminate_assume(assump, symbol=expr) diff --git a/sympy/queries/handlers/__init__.py b/sympy/queries/handlers/__init__.py index 7f36e1b..474cd92 100644 --- a/sympy/queries/handlers/__init__.py +++ b/sympy/queries/handlers/__init__.py @@ -1,3 +1,4 @@ +from sympy.logic.boolalg import conjuncts from sympy.queries import Q, ask class AskHandler(object): @@ -19,7 +20,8 @@ class AskCommutativeHandler(CommonHandler): @staticmethod def Symbol(expr, assumptions): """Objects are expected to be commutative unless otherwise stated""" - for assump in assumptions: + if assumptions is True: return True + for assump in conjuncts(assumptions): if assump.expr == expr and assump.key == 'commutative': return assump.value return True diff --git a/sympy/queries/handlers/calculus.py b/sympy/queries/handlers/calculus.py index 17449db..dfa4d65 100644 --- a/sympy/queries/handlers/calculus.py +++ b/sympy/queries/handlers/calculus.py @@ -2,6 +2,7 @@ This module contains query handlers resposible for calculus queries: infinitesimal, bounded, etc. """ +from sympy.logic.boolalg import conjuncts from sympy.queries import Q, ask from sympy.queries.handlers import CommonHandler @@ -60,7 +61,8 @@ class AskBoundedHandler(CommonHandler): @staticmethod def Symbol(expr, assumptions): - for assump in assumptions: + if assumptions is True: return False + for assump in conjuncts(assumptions): if assump.expr == expr and assump.key == 'bounded': return assump.value return False diff --git a/sympy/queries/handlers/ntheory.py b/sympy/queries/handlers/ntheory.py index 772a9bd..0c62c47 100644 --- a/sympy/queries/handlers/ntheory.py +++ b/sympy/queries/handlers/ntheory.py @@ -160,7 +160,7 @@ def Add(expr, assumptions): @staticmethod def Integer(expr, assumptions): - return expr % 2 == 0 + return not bool(expr.p & 1) @staticmethod def Rational(expr, assumptions): diff --git a/sympy/queries/handlers/order.py b/sympy/queries/handlers/order.py index 4b59202..5b75ad4 100644 --- a/sympy/queries/handlers/order.py +++ b/sympy/queries/handlers/order.py @@ -1,6 +1,7 @@ """ AskHandlers related to order relations: positive, negative, etc. """ +from sympy.logic.boolalg import fuzzy_not from sympy.utilities import all # python2.4 compatibility from sympy.queries import Q, ask from sympy.queries.handlers import CommonHandler @@ -8,8 +9,17 @@ class AskNegativeHandler(CommonHandler): """ - Handler for key 'negative' - Test that an expression is less (strict) than zero + This is called by ask() when key='negative' + + Test that an expression is less (strict) than zero. + + Examples: + + >>> from sympy import * + >>> ask(pi+1, Q.negative) # this calls AskNegativeHandler.Add + False + >>> ask(pi**2, Q.negative) # this calls AskNegativeHandler.Pow + False """ @staticmethod @@ -54,16 +64,20 @@ def Mul(expr, assumptions): @staticmethod def Pow(expr, assumptions): + """ + Real ** Even -> NonNegative + Real ** Odd -> same_as_base + NonNegative ** Positive -> NonNegative + """ if expr.is_number: return AskNegativeHandler._number(expr, assumptions) - if ask(expr.base, Q.negative, assumptions): - if ask(expr.exp, Q.odd, assumptions): - return True - if ask(expr.exp, Q.even, assumptions): + if ask(expr.base, Q.real, assumptions): + if ask(expr.base, Q.positive, assumptions): return False - elif ask(expr.base, Q.positive, assumptions): - if ask(expr.exp, Q.real, assumptions): + if ask(expr.exp, Q.even, assumptions): return False + if ask(expr.exp, Q.odd, assumptions): + return ask(expr.base, Q.negative, assumptions) @staticmethod def ImaginaryUnit(expr, assumptions): diff --git a/sympy/queries/handlers/sets.py b/sympy/queries/handlers/sets.py index 23de759..50ecc51 100644 --- a/sympy/queries/handlers/sets.py +++ b/sympy/queries/handlers/sets.py @@ -44,7 +44,7 @@ def Mul(expr, assumptions): if arg.is_Rational: if arg.q == 2: return ask(2*expr, Q.even, assumptions) - if arg.q % 2 == 1: + if ~(arg.q & 1): return None elif ask(arg, Q.irrational, assumptions): if _output: diff --git a/sympy/queries/tests/test_query.py b/sympy/queries/tests/test_query.py index e96ce7e..5de69df 100644 --- a/sympy/queries/tests/test_query.py +++ b/sympy/queries/tests/test_query.py @@ -687,6 +687,7 @@ def test_integer(): assert ask(2*x, Q.integer, Assume(x, Q.prime)) == True assert ask(2*x, Q.integer, Assume(x, Q.rational)) == None assert ask(2*x, Q.integer, Assume(x, Q.real)) == None + assert ask(sqrt(2)*x, Q.integer, Assume(x, Q.integer)) == False assert ask(x/2, Q.integer, Assume(x, Q.odd)) == False assert ask(x/2, Q.integer, Assume(x, Q.even)) == True @@ -712,6 +713,10 @@ def test_negative(): assert ask(x+y, Q.negative, Assume(x, Q.negative) &\ Assume(y, Q.negative)) == True + assert ask(x**2, Q.negative) == None + assert ask(x**2, Q.negative, Assume(x, Q.real)) == False + assert ask(x**1.4, Q.negative, Assume(x, Q.real)) == None + assert ask(x*y, Q.negative) == None assert ask(x*y, Q.negative, Assume(x, Q.positive) & \ Assume(y, Q.positive)) == False -- 1.6.4 --~--~---------~--~----~------------~-------~--~----~ You received this message because you are subscribed to the Google Groups "sympy-patches" group. To post to this group, send email to sympy-patches@googlegroups.com To unsubscribe from this group, send email to sympy-patches+unsubscr...@googlegroups.com For more options, visit this group at http://groups.google.com/group/sympy-patches?hl=en -~----------~----~----~----~------~----~------~--~---