Need help with symbolic polynomials,

52 views
Skip to first unread message

Ha

unread,
Apr 29, 2022, 7:33:36 AM4/29/22
to sage-support
Hi,
I need to create a polynomial ring with arbitrary number of variables [n] and
at some point during computation should be able to substitute values
for a subset of variables.   I can use the following method to generate
my ring:
##--------------------------------------------
n=2
F = GF(7)
Rx=PolynomialRing(F,n,'x')
X=Rx.gens()
##----------------------------------------------
But if I take an element f = x0+x1 then how to substitute values for x0 and x1?
In general I could use f(x0 = 1, x1 = 1) but with above method this doesnot seem to work. 

Any help is highly appreciated....

Nils Bruin

unread,
Apr 29, 2022, 11:55:48 AM4/29/22
to sage-support
Can you explain a little more about what does not work? When I try to replicate your example, everything works as expected:

sage: n=2
....: F = GF(7)
....: Rx=PolynomialRing(F,n,'x')
....: X=Rx.gens()
sage: f=X[0]+X[1]
sage: f(x0=1)
x1 + 1
sage: f(x0=1,x1=1)
2

Alternatively you can evaluate using positional arguments: in a polynomial ring there is a clear implied order on the generators, so the following is unambiguous (and accepted):

sage: f(1,1) #gives values for x0 and x1 in order
2

Ha

unread,
May 5, 2022, 5:03:30 AM5/5/22
to sage-support
Thanks for your reply Bruin.
I hope the following code clarifies what I am looking for:

##---------------------------------------------------------------------------------------------------------------------------------------------
#
n=10

F = GF(7)
Rx=PolynomialRing(F,n,'x')
X=Rx.gens()
f= Rx.random_element()
print(f)
#If I want to evaluate f at specific variables say x0 = 1, x5 = 7, then I can easily do it as
print(f(x0 = 1, x5 = 7))
#On the other hand, suppose I want to evaluate f at  xi = a, xj = b, where 1<= i, j <= n vary. I  want to have something like
f(X[i] = 1, X[j] = 5) # and supply values of i, j as input parameters.  Is this possible?
#
##---------------------------------------------------------------------------------------------------------------------------------------------

For Example:  I tried this:

f(X[1] = 1, X[2] = 5) 

and got this error:

File "<ipython-input-6-3b58a4eab255>", line 10 f(X[Integer(1)] = Integer(1), X[Integer(2)] = Integer(5))
^ SyntaxError: keyword can't be an expression

Nils Bruin

unread,
May 5, 2022, 5:22:52 PM5/5/22
to sage-support
On Thursday, 5 May 2022 at 02:03:30 UTC-7 Ha wrote:
For Example:  I tried this:

f(X[1] = 1, X[2] = 5) 

and got this error:

File "<ipython-input-6-3b58a4eab255>", line 10 f(X[Integer(1)] = Integer(1), X[Integer(2)] = Integer(5))
^ SyntaxError: keyword can't be an expression

Indeed, that does not work. The syntax f(x0=1,x1=5) works via python's keyword parameter mechanism. For it to work. the keyword argument used (x0 and x1 in the example) must match the print names of the variables of the polynomial ring. Those print names are x0,x1,...,x9 in your example. The names X[1] and X[2] do not match. What's worse: they are not valid python keywords, as the error says! So you don't even get to the matching phase.

What you would need is the *value* of X[1], X[2] instead (which is 'x1' and 'x2' respectively).

Python has some magic that allows you to specify the keyword names through expressions:

f(**{X[1]: 1, X[2]: 5})

should do the trick. It basically evaluates to f(**{'x1': 1, 'x2': 5}), and f(x1=1,x2=5) basically translates to f(**{'x1':1,'x2':5}) as well.

The keyword trick is really just there for convenience. The workarounds above may reduce convenience by quite a bit, so perhaps you prefer to just use "full evaluation" instead. For instance, for your example, you could do

v=list(X)
v[1]=1
v[2]=5
f(v)

(as presented here, it's less compact, but in your actual application it may be more direct)

Ha

unread,
May 6, 2022, 4:52:09 AM5/6/22
to sage-support
Thanks Bruin, that was really helpful.
Reply all
Reply to author
Forward
0 new messages