module Symtegration.Polynomial.Differential
(
canonical,
splitFactor,
splitSquarefreeFactor,
extend,
consistent,
)
where
import Data.Monoid (Sum (..))
import Symtegration.Polynomial
import Symtegration.Polynomial.Rational
splitSquarefreeFactor ::
(Polynomial p e c, Eq (p e c), Num (p e c), Eq c, Fractional c) =>
(p e c -> p e c) ->
p e c ->
[(p e c, p e c)]
splitSquarefreeFactor :: forall (p :: * -> * -> *) e c.
(Polynomial p e c, Eq (p e c), Num (p e c), Eq c, Fractional c) =>
(p e c -> p e c) -> p e c -> [(p e c, p e c)]
splitSquarefreeFactor p e c -> p e c
derivation p e c
p = (p e c -> (p e c, p e c)) -> [p e c] -> [(p e c, p e c)]
forall a b. (a -> b) -> [a] -> [b]
map p e c -> (p e c, p e c)
split [p e c]
ps
where
ps :: [p e c]
ps = p e c -> [p e c]
forall (p :: * -> * -> *) e c.
(Polynomial p e c, Eq (p e c), Num (p e c), Eq c, Fractional c) =>
p e c -> [p e c]
squarefree p e c
p
split :: p e c -> (p e c, p e c)
split p e c
q = (p e c
qn, p e c
qs)
where
qs :: p e c
qs = p e c -> p e c -> p e c
forall (p :: * -> * -> *) e c.
(Polynomial p e c, Eq (p e c), Num (p e c), Fractional c) =>
p e c -> p e c -> p e c
greatestCommonDivisor p e c
q (p e c -> p e c) -> p e c -> p e c
forall a b. (a -> b) -> a -> b
$ p e c -> p e c
derivation p e c
q
(p e c
qn, p e c
_) = p e c
q p e c -> p e c -> (p e c, p e c)
forall (p :: * -> * -> *) e c.
(Polynomial p e c, Eq (p e c), Num (p e c), Fractional c) =>
p e c -> p e c -> (p e c, p e c)
`divide` p e c
qs
splitFactor ::
(Polynomial p e c, Eq (p e c), Num (p e c), Eq c, Fractional c) =>
(p e c -> p e c) ->
p e c ->
(p e c, p e c)
splitFactor :: forall (p :: * -> * -> *) e c.
(Polynomial p e c, Eq (p e c), Num (p e c), Eq c, Fractional c) =>
(p e c -> p e c) -> p e c -> (p e c, p e c)
splitFactor p e c -> p e c
derivation p e c
p = (p e c, p e c) -> [(p e c, p e c)] -> Int -> (p e c, p e c)
forall {t} {a} {b}.
(Integral t, Num a, Num b) =>
(a, b) -> [(a, b)] -> t -> (a, b)
compose (p e c
1, p e c
1) [(p e c, p e c)]
factors (Int
1 :: Int)
where
factors :: [(p e c, p e c)]
factors = (p e c -> p e c) -> p e c -> [(p e c, p e c)]
forall (p :: * -> * -> *) e c.
(Polynomial p e c, Eq (p e c), Num (p e c), Eq c, Fractional c) =>
(p e c -> p e c) -> p e c -> [(p e c, p e c)]
splitSquarefreeFactor p e c -> p e c
derivation p e c
p
compose :: (a, b) -> [(a, b)] -> t -> (a, b)
compose (a, b)
split [] t
_ = (a, b)
split
compose (a
pn, b
ps) ((a
qn, b
qs) : [(a, b)]
fs) t
n = (a, b) -> [(a, b)] -> t -> (a, b)
compose (a
pn a -> a -> a
forall a. Num a => a -> a -> a
* (a
qn a -> t -> a
forall a b. (Num a, Integral b) => a -> b -> a
^ t
n), b
ps b -> b -> b
forall a. Num a => a -> a -> a
* (b
qs b -> t -> b
forall a b. (Num a, Integral b) => a -> b -> a
^ t
n)) [(a, b)]
fs (t
n t -> t -> t
forall a. Num a => a -> a -> a
+ t
1)
canonical ::
(Polynomial p e c, Eq (p e c), Num (p e c), Eq c, Fractional c) =>
(p e c -> p e c) ->
Function (p e c) ->
(p e c, Function (p e c), Function (p e c))
canonical :: forall (p :: * -> * -> *) e c.
(Polynomial p e c, Eq (p e c), Num (p e c), Eq c, Fractional c) =>
(p e c -> p e c)
-> Function (p e c) -> (p e c, Function (p e c), Function (p e c))
canonical p e c -> p e c
_ x :: Function (p e c)
x@(Function p e c
_ p e c
0) = (p e c
0, Function (p e c)
0, Function (p e c)
x)
canonical p e c -> p e c
derivation (Function p e c
a p e c
d)
| Just (p e c
b, p e c
c) <- Maybe (p e c, p e c)
xs = (p e c
q, p e c -> p e c -> Function (p e c)
forall (p :: * -> * -> *) e c.
(Polynomial p e c, Eq (p e c), Num (p e c), Fractional c) =>
p e c -> p e c -> Function (p e c)
fromPolynomials p e c
c p e c
dn, p e c -> p e c -> Function (p e c)
forall (p :: * -> * -> *) e c.
(Polynomial p e c, Eq (p e c), Num (p e c), Fractional c) =>
p e c -> p e c -> Function (p e c)
fromPolynomials p e c
b p e c
ds)
| Bool
otherwise = (p e c
q, Function (p e c)
0, p e c -> p e c -> Function (p e c)
forall (p :: * -> * -> *) e c.
(Polynomial p e c, Eq (p e c), Num (p e c), Fractional c) =>
p e c -> p e c -> Function (p e c)
fromPolynomials p e c
r p e c
d)
where
a' :: p e c
a' = c -> p e c -> p e c
forall (p :: * -> * -> *) e c.
Polynomial p e c =>
c -> p e c -> p e c
scale (c
1 c -> c -> c
forall a. Fractional a => a -> a -> a
/ p e c -> c
forall (p :: * -> * -> *) e c. Polynomial p e c => p e c -> c
leadingCoefficient p e c
d) p e c
a
d' :: p e c
d' = c -> p e c -> p e c
forall (p :: * -> * -> *) e c.
Polynomial p e c =>
c -> p e c -> p e c
scale (c
1 c -> c -> c
forall a. Fractional a => a -> a -> a
/ p e c -> c
forall (p :: * -> * -> *) e c. Polynomial p e c => p e c -> c
leadingCoefficient p e c
d) p e c
d
(p e c
q, p e c
r) = p e c
a' p e c -> p e c -> (p e c, p e c)
forall (p :: * -> * -> *) e c.
(Polynomial p e c, Eq (p e c), Num (p e c), Fractional c) =>
p e c -> p e c -> (p e c, p e c)
`divide` p e c
d'
(p e c
dn, p e c
ds) = (p e c -> p e c) -> p e c -> (p e c, p e c)
forall (p :: * -> * -> *) e c.
(Polynomial p e c, Eq (p e c), Num (p e c), Eq c, Fractional c) =>
(p e c -> p e c) -> p e c -> (p e c, p e c)
splitFactor p e c -> p e c
derivation p e c
d'
xs :: Maybe (p e c, p e c)
xs = p e c -> p e c -> p e c -> Maybe (p e c, p e c)
forall (p :: * -> * -> *) e c.
(Polynomial p e c, Eq (p e c), Num (p e c), Fractional c) =>
p e c -> p e c -> p e c -> Maybe (p e c, p e c)
diophantineEuclidean p e c
dn p e c
ds p e c
r
consistent ::
(Eq a, Num a) =>
(a -> a) ->
a ->
a ->
Bool
consistent :: forall a. (Eq a, Num a) => (a -> a) -> a -> a -> Bool
consistent a -> a
derivation a
a a
b = Bool
additive Bool -> Bool -> Bool
&& Bool
productive
where
additive :: Bool
additive = a -> a
derivation (a
a a -> a -> a
forall a. Num a => a -> a -> a
+ a
b) a -> a -> Bool
forall a. Eq a => a -> a -> Bool
== a -> a
derivation a
a a -> a -> a
forall a. Num a => a -> a -> a
+ a -> a
derivation a
b
productive :: Bool
productive = a -> a
derivation (a
a a -> a -> a
forall a. Num a => a -> a -> a
* a
b) a -> a -> Bool
forall a. Eq a => a -> a -> Bool
== a
a a -> a -> a
forall a. Num a => a -> a -> a
* a -> a
derivation a
b a -> a -> a
forall a. Num a => a -> a -> a
+ a
b a -> a -> a
forall a. Num a => a -> a -> a
* a -> a
derivation a
a
extend :: (Polynomial p e c, Num (p e c), Eq c, Num c) => (c -> c) -> p e c -> p e c -> p e c
extend :: forall (p :: * -> * -> *) e c.
(Polynomial p e c, Num (p e c), Eq c, Num c) =>
(c -> c) -> p e c -> p e c -> p e c
extend c -> c
derivation p e c
w p e c
p = Sum (p e c) -> p e c
forall a. Sum a -> a
getSum (Sum (p e c) -> p e c) -> Sum (p e c) -> p e c
forall a b. (a -> b) -> a -> b
$ (e -> c -> Sum (p e c)) -> p e c -> Sum (p e c)
forall m. Monoid m => (e -> c -> m) -> p e c -> m
forall (p :: * -> * -> *) e c m.
(Polynomial p e c, Monoid m) =>
(e -> c -> m) -> p e c -> m
foldTerms (\e
e c
c -> p e c -> Sum (p e c)
forall a. a -> Sum a
Sum (p e c -> Sum (p e c)) -> p e c -> Sum (p e c)
forall a b. (a -> b) -> a -> b
$ e -> c -> p e c
derive e
e c
c) p e c
p
where
derive :: e -> c -> p e c
derive e
e c
c = c -> p e c -> p e c
forall (p :: * -> * -> *) e c.
Polynomial p e c =>
c -> p e c -> p e c
scale (c -> c
derivation c
c) (e -> p e c
forall (p :: * -> * -> *) e c. Polynomial p e c => e -> p e c
power e
e) p e c -> p e c -> p e c
forall a. Num a => a -> a -> a
+ c -> p e c -> p e c
forall (p :: * -> * -> *) e c.
Polynomial p e c =>
c -> p e c -> p e c
scale (c
c c -> c -> c
forall a. Num a => a -> a -> a
* e -> c
forall a b. (Integral a, Num b) => a -> b
fromIntegral e
e) (e -> p e c
forall (p :: * -> * -> *) e c. Polynomial p e c => e -> p e c
power (e -> p e c) -> e -> p e c
forall a b. (a -> b) -> a -> b
$ e
e e -> e -> e
forall a. Num a => a -> a -> a
- e
1) p e c -> p e c -> p e c
forall a. Num a => a -> a -> a
* p e c
w