| Safe Haskell | None |
|---|---|
| Language | GHC2024 |
Circuit.Diff.Param
Description
Parameterised reverse-mode automatic differentiation.
DiffP is a differentiable operation with parameters p, input a and
output b. Running forward produces the output; the backward pass, given
a cotangent on the output, produces the input cotangent and parameter
gradients.
This is the same shape as Diff from circuits-ad, but with
an explicit parameter carrier p. When p = () and the parameter
gradient is discarded, DiffP reduces to Diff (see toParam and
fromParam).
The representation is the denotation p -> a -> (b, b -> (a, p)) rather
than a pair of separate forward/backward fields, so it stays aligned with
the monomial/lens reading of AD.
Synopsis
- newtype DiffP p a b = DiffP {
- runDiffP :: p -> a -> (b, b -> (a, p))
- data TensorPrim p a b = TensorPrim {
- primForward :: p -> a -> b
- primBackward :: p -> a -> b -> (a, p)
- fromPrim :: TensorPrim p a b -> DiffP p a b
- toPrim :: DiffP p a b -> TensorPrim p a b
- residual :: Num a => DiffP p a a -> DiffP p a a
- splitP :: DiffP p1 a1 b1 -> DiffP p2 a2 b2 -> DiffP (p1, p2) (a1, a2) (b1, b2)
- joinP :: Num a => DiffP p1 a b1 -> DiffP p2 a b2 -> DiffP (p1, p2) a (b1, b2)
- toParam :: forall {k} (q :: k) a b. Diff q a b -> DiffP () a b
- fromParam :: DiffP () a b -> Diff () a b
Parameterised differentiable arrow
A differentiable operation with parameters p, input a and output b.
The forward pass closes over the parameter p and input a, producing an
output b and a pullback. The pullback maps an output cotangent db to
an input cotangent da and a parameter gradient dp.
This is a point-dependent lens: the parameter is part of the position, not an extra layer.
Instances
| MergeZero (->) p => Channel (,) (DiffP p :: Type -> Type -> Type) Source # | Structural associator for nested pairs. No parameters are touched. The superclass 'Category (DiffP p)' requires 'MergeZero (->) p', so the instance carries the same constraint even though the structural maps themselves ignore the parameter. |
| MergeZero (->) p => Action (,) (DiffP p :: Type -> Type -> Type) Source # | |
Defined in Circuit.Diff.Param | |
| MergeZero (->) p => Tensor (,) (DiffP p :: Type -> Type -> Type) Source # | |
| MergeZero (->) p => Unital (,) (DiffP p :: Type -> Type -> Type) Source # | Parallel composition runs both arrows with the same parameter The parameter is treated as an input value, not a state, so it can be
passed to both branches without a comonoid structure. Only the output
gradients need
|
| MergeZero (->) p => Category (DiffP p :: Type -> Type -> Type) Source # | Sequential composition threads the same parameter Identity returns a zero parameter gradient. This instance needs
Parameter gradients from both composed arrows accumulate (not just the
outer one).
|
| (Zero (->) a, Zero (->) p) => Discard (DiffP p :: Type -> Type -> Type) (a :: Type) Source # | |
Defined in Circuit.Diff.Param | |
| (Zero (->) a, Zero (->) p) => Zero (DiffP p :: Type -> Type -> Type) (a :: Type) Source # | |
Defined in Circuit.Diff.Param | |
| (Merge (->) a, Zero (->) p) => Copy (DiffP p) a Source # | Copy in
|
Defined in Circuit.Diff.Param | |
| (Merge (->) a, Zero (->) p) => Merge (DiffP p) a Source # | Add in
|
Defined in Circuit.Diff.Param | |
Primitive contract
data TensorPrim p a b Source #
A primitive contract with separate forward and backward fields, easier to read and write for dense linear-algebra primitives.
Constructors
| TensorPrim | |
Fields
| |
fromPrim :: TensorPrim p a b -> DiffP p a b Source #
Convert a TensorPrim into a DiffP.
toPrim :: DiffP p a b -> TensorPrim p a b Source #
Convert a DiffP into a TensorPrim.
Wiring helpers
residual :: Num a => DiffP p a a -> DiffP p a a Source #
Add a residual connection around an operation.
forward: y = x + op(x) backward: dx = dy + dOp
joinP :: Num a => DiffP p1 a b1 -> DiffP p2 a b2 -> DiffP (p1, p2) a (b1, b2) Source #
Pair two operations that share the same input type but produce independent outputs. Input cotangents are added; parameter gradients are paired.
Relationship to the phantom-tagged Diff arrow
fromParam :: DiffP () a b -> Diff () a b Source #
Project a parameter-free 'DiffP ()' back into the phantom-tagged
Diff arrow.
This is a section/retract pair with toParam:
fromParam . toParam = id for the parameter-free fragment.
>>>let d = Diff (\x -> (x * x, \dy -> 2 * x * dy)) :: Diff () Double Double>>>let (y, pb) = runDiff (fromParam (toParam d)) 3.0>>>y9.0>>>pb 1.06.0