@@ -41,23 +41,7 @@ is equivalent to:
4141 subs(polynomial, (x=>1, y=>2))
4242"""
4343function substitute (st:: _AST , p:: _APL , s:: AbstractMultiSubstitution )
44- return substitute (st, p, pair_zip (_monomial_vector_to_variable_tuple (s)))
45- end
46-
47- # Evaluate the stream
48- # If I do s2..., then
49- # subs(x, x=>x+y, y=>2) would call substitute(Subs(), x+y, y=>2)
50- # subs(x, x=>1, y=>2) would call substitute(Subs(), 1, y=>2)
51- # so it would force use to also define
52- # sustitute(::_AST, ..., ::AbstractSubstitution...) for Any, _APL and RationalPoly.
53- # substitute(st::_AST, p::_APL, s1::AbstractSubstitution, s2::AbstractSubstitution...) = substitute(st, substitute(st, p, s1), s2...)
54- function substitute (
55- st:: _AST ,
56- p:: _APL ,
57- s1:: AbstractSubstitution ,
58- s2:: AbstractSubstitution... ,
59- )
60- return substitute (st, substitute (st, p, s1), s2)
44+ return substitute (st, p, _flatten_subs (s))
6145end
6246
6347# # Variables
@@ -82,35 +66,70 @@ function powersubstitute(
8266 return powersubstitute (st, s, p) * powersubstitute (st, s, p2... )
8367end
8468
85- function _promote_subs (S, T, s:: Substitution )
86- # `T` is a constant
87- return T
69+ function _promote_subs (
70+ S,
71+ :: Type{V} ,
72+ s:: Substitution ,
73+ ) where {V<: AbstractVariable }
74+ return MA. promote_operation (substitute, S, V, typeof (s))
8875end
8976
90- function _promote_subs (S, T :: Type{<:Union{RationalPoly,_APL}} , s:: Substitution )
91- return MA . promote_operation (substitute, S, T, typeof (s))
77+ function _flatten_subs ( s:: AbstractMultiSubstitution )
78+ return pair_zip ( _monomial_vector_to_variable_tuple (s))
9279end
9380
94- function _promote_subs (S, T, s:: AbstractMultiSubstitution )
95- return _promote_subs (
96- S,
97- T,
98- pair_zip (_monomial_vector_to_variable_tuple (s))... ,
99- )
81+ function _flatten_subs (s:: Substitution )
82+ return (s,)
10083end
10184
102- function _promote_subs (
103- S,
104- T,
105- head:: AbstractSubstitution ,
85+ # Turn a tuple of `AbstractSubstitution` into a `Tuple` if `Substitution`
86+ function _flatten_subs (
87+ s:: AbstractSubstitution ,
10688 tail:: Vararg{AbstractSubstitution,N} ,
10789) where {N}
108- return _promote_subs (S, _promote_subs (S, T, head), tail... )
90+ return (_flatten_subs (s)... , _flatten_subs (tail... )... )
91+ end
92+
93+ function power_promote (
94+ S,
95+ :: Type{V} ,
96+ s:: Substitutions ,
97+ ) where {V<: AbstractVariable }
98+ T = MA. promote_operation (substitute, S, V, typeof .(_flatten_subs (s... ))... )
99+ return MA. promote_operation (* , T, T)
100+ end
101+
102+ function power_promote (
103+ S,
104+ :: Vector{V} ,
105+ s:: Substitutions ,
106+ ) where {V<: AbstractVariable }
107+ return power_promote (S, V, s)
108+ end
109+
110+ function power_promote (
111+ S,
112+ :: Tuple{V} ,
113+ s:: Substitutions ,
114+ ) where {V<: AbstractVariable }
115+ return power_promote (S, V, s)
116+ end
117+
118+ function power_promote (
119+ S,
120+ vars:: Tuple{V,Vararg{AbstractVariable,N}} ,
121+ s:: Substitutions ,
122+ ) where {V<: AbstractVariable ,N}
123+ return MA. promote_operation (
124+ * ,
125+ power_promote (S, V, s),
126+ power_promote (S, Base. tail (vars), s),
127+ )
109128end
110129
111130function substitute (st:: _AST , m:: AbstractMonomial , s:: Substitutions )
112131 if isconstant (m)
113- return one (_promote_subs (typeof (st), typeof (m), s... ))
132+ return one (power_promote (typeof (st), variables (m), s))
114133 else
115134 return powersubstitute (st, s, powers (m)... )
116135 end
0 commit comments