Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add difference between Zero and DoesNotExist to FAQ #156

Merged
merged 7 commits into from
Jan 20, 2020
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
14 changes: 14 additions & 0 deletions docs/src/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -430,3 +430,17 @@ As a rule keyword arguments tend to control side-effects, like logging verbosity
or to be functionality changing to perform a different operation, e.g. `dims=3`, and thus not differentiable.
To the best of our knowledge no Julia AD system, with support for the definition of custom primitives, supports differentiating with respect to keyword arguments.
At some point in the future ChainRules may support these. Maybe.


### What is the difference between `Zero` and `DoesNotExist` ?
`Zero` and `DoesNotExist` act almost exactly the same in practice: they result in no change whenever added to anything.
Odds are if you write a rule that returns the wrong one everything will just work fine.
We provide both to allow for clearer writing of rules, and easier debugging.

`Zero()` represents the fact that if one perturbs (adds a small change to) the matching primal there will be no change in the behavour of the primal function.
For example in `fst(x,y) = x`, then the derivative of `fst` with respect to `y` is `Zero()`.
`fst(10, 5) == 10` and if we add `0,1` to `5` we still get `fst(10, 5.1)=10`.

`DoesNotExist()` represents the fact that if one perturbs the matching primal, the primal function will now error.
For example in `access(xs, n) = xs[n]` then the derivative of `access` with respect to `n` is `DoesNotExist()`.
`access([10, 20, 30], 2) = 20`, but if we add `0.1` to `2` we get `access([10, 20, 30], 2.1)` which errors as indexing can't be applied at fractional indexes.