Skip to content

Commit 94219d4

Browse files
committed
fix plethysm with f having finite support
1 parent a2e9ed7 commit 94219d4

File tree

2 files changed

+42
-24
lines changed

2 files changed

+42
-24
lines changed

src/sage/data_structures/stream.py

Lines changed: 35 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -1671,7 +1671,8 @@ class Stream_plethysm(Stream_binary):
16711671
INPUT:
16721672
16731673
- ``f`` -- a :class:`Stream`
1674-
- ``g`` -- a :class:`Stream` with positive order
1674+
- ``g`` -- a :class:`Stream` with positive order, unless ``f`` is
1675+
of :class:`Stream_exact`.
16751676
- ``p`` -- the powersum symmetric functions
16761677
- ``ring`` (optional, default ``None``) -- the ring the result
16771678
should be in, by default ``p``
@@ -1702,12 +1703,20 @@ class Stream_plethysm(Stream_binary):
17021703
s[1, 1, 1] + s[2, 1] + 2*s[3],
17031704
s[1, 1, 1, 1] + s[2, 1, 1] + 3*s[3, 1] + 2*s[4]]
17041705
1706+
This class also handles the plethysm of an exact stream with a
1707+
stream of order `0`::
1708+
1709+
sage: from sage.data_structures.stream import Stream_exact
1710+
sage: f = Stream_exact([s[1]], True, order=1)
1711+
sage: g = Stream_function(lambda n: s[n], s, True, 0)
1712+
sage: r = Stream_plethysm(f, g, p, s)
1713+
sage: [r[n] for n in range(3)]
1714+
[s[], s[1], s[2]]
1715+
17051716
TESTS:
17061717
17071718
Check corner cases::
17081719
1709-
sage: from sage.data_structures.stream import Stream_exact
1710-
sage: p = SymmetricFunctions(QQ).p()
17111720
sage: f0 = Stream_exact([p([])], True)
17121721
sage: f1 = Stream_exact([p[1]], True, order=1)
17131722
sage: f2 = Stream_exact([p[2]], True, order=2 )
@@ -1768,7 +1777,10 @@ def __init__(self, f, g, p, ring=None, include=None, exclude=None):
17681777
else:
17691778
self._tensor_power = None
17701779
p_f = Stream_map_coefficients(f, lambda x: x, p)
1771-
1780+
if isinstance(f, Stream_exact) and not f._constant:
1781+
self._degree_f = f._degree
1782+
else:
1783+
self._degree_f = None
17721784
self._degree_one = _variables_recursive(R, include=include, exclude=exclude)
17731785
super().__init__(p_f, p_g, f._is_sparse, val)
17741786

@@ -1799,9 +1811,13 @@ def get_coefficient(self, n):
17991811
4*s[1, 1, 1, 1, 1] + 4*s[2, 1, 1, 1] + 2*s[2, 2, 1] + 2*s[3, 1, 1] + s[3, 2] + s[4, 1] + s[5]]
18001812
"""
18011813
if not n: # special case of 0
1802-
if self._tensor_power is None:
1803-
return self._left[0]
1804-
return self._basis(self._left[0].coefficient([]))
1814+
if self._right[0]:
1815+
assert self._degree_f is not None, "the plethysm with a lazy symmetric function of valuation 0 is defined only for symmetric functions of finite support"
1816+
1817+
return sum((c * self._compute_product(n, la)
1818+
for k in range(self._left._approximate_order, self._degree_f)
1819+
for la, c in self._left[k]),
1820+
self._basis.zero())
18051821

18061822
return sum((c * self._compute_product(n, la)
18071823
for k in range(self._left._approximate_order, n+1)
@@ -1823,18 +1839,25 @@ def _compute_product(self, n, la):
18231839
sage: A = h._compute_product(7, Partition([2, 1])); A
18241840
1/12*p[2, 2, 1, 1, 1] + 1/4*p[2, 2, 2, 1] + 1/6*p[3, 2, 2]
18251841
+ 1/12*p[4, 1, 1, 1] + 1/4*p[4, 2, 1] + 1/6*p[4, 3]
1826-
sage: A == p[2,1](s[2] + s[3]).homogeneous_component(7)
1842+
sage: A == p[2, 1](s[2] + s[3]).homogeneous_component(7)
18271843
True
18281844
18291845
sage: p2 = tensor([p, p])
18301846
sage: f = Stream_zero(True) # irrelevant for this test
18311847
sage: g = Stream_function(lambda n: sum(tensor([p[k], p[n-k]]) for k in range(n+1)), p2, True, 1)
18321848
sage: h = Stream_plethysm(f, g, p2)
18331849
sage: A = h._compute_product(7, Partition([2, 1]))
1834-
sage: B = p[2,1](sum(g[n] for n in range(7)))
1850+
sage: B = p[2, 1](sum(g[n] for n in range(7)))
18351851
sage: B = p2.element_class(p2, {m: c for m, c in B if sum(mu.size() for mu in m) == 7})
18361852
sage: A == B
18371853
True
1854+
1855+
sage: f = Stream_zero(True) # irrelevant for this test
1856+
sage: g = Stream_function(lambda n: s[n], p, True, 0)
1857+
sage: h = Stream_plethysm(f, g, p)
1858+
sage: B = p[2, 2, 1](sum(s[i] for i in range(7)))
1859+
sage: all(h._compute_product(k, Partition([2, 2, 1])) == B.restrict_degree(k) for k in range(7))
1860+
True
18381861
"""
18391862
ret = self._basis.zero()
18401863
la_exp = la.to_exp()
@@ -1846,10 +1869,10 @@ def _compute_product(self, n, la):
18461869
if any(d < self._right._approximate_order * m
18471870
for m, d in zip(exp, k)):
18481871
continue
1849-
temp = self._basis.one()
1872+
prod = self._basis.one()
18501873
for i, m, d in zip(wgt, exp, k):
1851-
temp *= self._stretched_power_restrict_degree(i, m, d)
1852-
ret += temp
1874+
prod *= self._stretched_power_restrict_degree(i, m, d)
1875+
ret += prod
18531876
return ret
18541877

18551878
def _stretched_power_restrict_degree(self, i, m, d):

src/sage/rings/lazy_series.py

Lines changed: 7 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -4222,8 +4222,7 @@ def __call__(self, *g, check=True):
42224222
True
42234223
sage: f = 1 / (1 - S(s[2]))
42244224
sage: g = S(s[1]) / (1 - S(s[1]))
4225-
sage: h = f(g)
4226-
sage: h
4225+
sage: f(g)
42274226
s[] + s[2] + (s[1,1,1]+2*s[2,1]+s[3])
42284227
+ (2*s[1,1,1,1]+4*s[2,1,1]+5*s[2,2]+5*s[3,1]+3*s[4])
42294228
+ (2*s[1,1,1,1,1]+10*s[2,1,1,1]+14*s[2,2,1]+18*s[3,1,1]+16*s[3,2]+14*s[4,1]+4*s[5])
@@ -4261,12 +4260,6 @@ def __call__(self, *g, check=True):
42614260
if len(g) != fP._arity:
42624261
raise ValueError("arity must be equal to the number of arguments provided")
42634262

4264-
# we actually do not need this
4265-
from sage.combinat.sf.sfa import is_SymmetricFunction
4266-
# if not all(isinstance(h, LazySymmetricFunction)
4267-
# or is_SymmetricFunction(h) or not h for h in g):
4268-
# raise ValueError("all arguments must be (possibly lazy) symmetric functions")
4269-
42704263
# Find a good parent for the result
42714264
from sage.structure.element import get_coercion_model
42724265
cm = get_coercion_model()
@@ -4291,12 +4284,14 @@ def __call__(self, *g, check=True):
42914284
g = g[0]
42924285
if (isinstance(self._coeff_stream, Stream_exact)
42934286
and not self._coeff_stream._constant):
4294-
f = self.symmetric_function()
4287+
42954288
if not isinstance(g, LazySymmetricFunction):
4289+
f = self.symmetric_function()
42964290
return f(g)
4297-
# g must be a LazySymmetricFunction
4291+
42984292
if (isinstance(g._coeff_stream, Stream_exact)
42994293
and not g._coeff_stream._constant):
4294+
f = self.symmetric_function()
43004295
gs = g.symmetric_function()
43014296
return P(f(gs))
43024297

@@ -4308,8 +4303,8 @@ def __call__(self, *g, check=True):
43084303
P = LazySymmetricFunctions(R)
43094304
g = P(g)
43104305

4311-
# self has (potentially) infinitely many terms
4312-
if check:
4306+
if check and not (isinstance(self._coeff_stream, Stream_exact)
4307+
and not self._coeff_stream._constant):
43134308
if g._coeff_stream._approximate_order == 0:
43144309
if g[0]:
43154310
raise ValueError("can only compose with a positive valuation series")

0 commit comments

Comments
 (0)