# Check that variable is integer

Dear Sage,

I define the following variable

sage: a = var('a')
sage: assume(a, 'integer')


How do I check that is variable is an integer? The following doese not seem to work in sage 5.2.

sage: a in ZZ
False
sage: 2 in ZZ
True
sage: assumptions()
[a is integer]


How should I check the assumption that a is an integer?

Best, Noud

edit retag close merge delete

Sort by » oldest newest most voted

I don't think there's a method that queries the assumptions data. You can write a simple function to test this using the output of assumptions():

sage: a=var('a')
sage: assume(a, 'integer')
sage: any('a is integer' in str(x) for x in assumptions())
True
sage: any('a is real' in str(x) for x in assumptions())
False


The assumptions function returns a list of GenericDeclaration objects which are turned into strings above.

sage: type(assumptions())
<class 'sage.symbolic.assumptions.GenericDeclaration'>


Beware that the only subsystem of Sage that respects (or takes account of) symbolic assumptions is Maxima. So some symbolic operations will "know" about the assumptions (the ones that use Maxima under the hood) and some won't.

more

Sorry to say this to you, but I think this is an extremely ugly solution. Is there an other solution to give a variable properties like being positive, or having real part, etc. So I might should have asked, is there a way to give variables extra properties, like being real, having real part, being imaginary, etc?

At some level you're going to need to query the global assumptions list which is returned by assumptions(). So whether you bury this in a new method of the symbolic expression type, or write your own top-level function to do it, its not going to get less "ugly", just more or less hidden. If you have a better method, let's see it.

I agree with you that it is indeed quite hard and maybe even impossible to do it in a nice way. Let me see if I can bury it in a new method of the symbolic expression type. This will give me some more insight in how Sage works. I'll mark your solution as the solution, since it is obvious a solution. ;) Thank you!

# Check if a variable is assumed to be integer

I found a 'nice and clean' way to check if a variable is assumed to be integer.

The only objection to calling it 'nice and clean' is that it uses the hidden attribute_assumption, which does not exist as a method. This could be a feature request, and it would not be hard to implement.

In short, this checks if the variable 'a' is assumed to be integer:

sage: a = var('a')
sage: assume(a, 'integer')
sage: 'integer' in (x._assumption for x in assumptions(a))
True


(Tested in Sage Version 6.3.beta5, released on 2014-07-01, but I'm sure this has been possible for a long time.)

## How could one find that out?

sage: version() # for reference
'Sage Version 6.3.beta5, Release Date: 2014-07-01'
sage: a = var('a')
sage: assume(a, 'integer')
sage: h = assumptions()
sage: h
[a is integer]
sage: ha = assumptions(a)
sage: ha
[a is integer]
sage: d = assumptions(a)
sage: d
a is integer
sage: type(d)
<class 'sage.symbolic.assumptions.GenericDeclaration'>


Now use the 'tab' key to check what methods are available for d:

sage: d.
d.assume       d.contradicts  d.dump         d.forget       d.rename       d.save
d.category     d.db           d.dumps        d.has          d.reset_name   d.version


and keep exploring:

sage: d.has(a)
True
sage: from sage.symbolic.assumptions import GenericDeclaration as GDecl


Read the documentation for GDecl, then the source code.

sage: GDecl?
sage: GDecl??


and detect the use of the _assumption attribute in the source code. Now play with it!

sage: d._assumption
'integer'
sage: 'integer' in (x._assumption for x in assumptions(a))
True


## Possible feature requests

This is beyond the scope of answering your question, but just in case someone finds it interesting and wants to open a trac ticket or two and/or change the code accordingly.

• a method 'assumptions' for the class sage.symbolic.assumptions.GenericDeclaration.

• make the is_integer method check for the 'integer' assumption as above, for symbolic variables. So far:

sage: a.is_integer()
False


However the source code for this method is

def is_integer(self):
"""
Return True if this expression is known to be an integer.

EXAMPLES::

sage: SR(5).is_integer()
True
"""
return self._gobj.info(info_integer)


in particular the docstring claims it should return True if the expression is known to be an integer.

more

This answer is given because the OP did not specify for what purpose (s)he wants the restriction.

The usual method in Sage outside of symbolics to ensure entities are integer, rational, real etc. is to work in the respective ring. So if you work with polynomials and want them to have integer coefficients use PolynomialRing(ZZ).

more

Sorry for resurrecting this question from Oct 2012 (saw it, found it interesting, found an answer going further than the existing one). I understand the intention in the question as follows: Main question: "It is clear how to declare the assumption that a symbolic variable is integer, but how can one check whether a symbolic variable has that assumption?" The original poster then illustrates that the natural way to try and check that, ie typing 'a in ZZ', fails. By contrast, it works when applied to '2'. Also, one easily checks that Sage knows about 'a' being an integer by typing 'assumptions()'. But I see your point: if we knew the goal pursued when the question arose, we could suggest better ways to achieve it, by working with more appropriate structures than the symbolic ring.