diff --git a/Project.toml b/Project.toml index a00e73c2..06f6ced5 100644 --- a/Project.toml +++ b/Project.toml @@ -1,6 +1,6 @@ name = "FiniteDifferences" uuid = "26cc04aa-876d-5657-8c51-4c34ba976000" -version = "0.10.3" +version = "0.10.4" [deps] LinearAlgebra = "37e2e46d-f89d-539d-b4ee-838fcccc9c8e" diff --git a/src/grad.jl b/src/grad.jl index 673aeb34..f02f849b 100644 --- a/src/grad.jl +++ b/src/grad.jl @@ -76,6 +76,7 @@ end j′vp(fdm, f, ȳ, xs...) = j′vp(fdm, xs->f(xs...), ȳ, xs)[1] function _j′vp(fdm, f, ȳ::Vector{<:Real}, x::Vector{<:Real}) + isempty(x) && return eltype(ȳ)[] # if x is empty, then so is the jacobian and x̄ return transpose(first(jacobian(fdm, f, x))) * ȳ end diff --git a/test/grad.jl b/test/grad.jl index 1bdaf953..29beee2d 100644 --- a/test/grad.jl +++ b/test/grad.jl @@ -140,15 +140,17 @@ using FiniteDifferences: grad, jacobian, _jvp, jvp, j′vp, _j′vp, to_vec end @testset "j′vp(::$T)" for T in (Float64,) - rng, N, M, fdm = MersenneTwister(123456), 2, 3, central_fdm(5, 1) - x, y = randn(rng, T, N), randn(rng, T, M) - z̄ = randn(rng, T, N + M) - xy = vcat(x, y) - x̄ȳ_manual = j′vp(fdm, xy->sin.(xy), z̄, xy)[1] - x̄ȳ_auto = j′vp(fdm, x->sin.(vcat(x[1], x[2])), z̄, (x, y))[1] - x̄ȳ_multi = j′vp(fdm, (x, y)->sin.(vcat(x, y)), z̄, x, y) - @test x̄ȳ_manual ≈ vcat(x̄ȳ_auto...) - @test x̄ȳ_manual ≈ vcat(x̄ȳ_multi...) + rng, fdm = MersenneTwister(123456), central_fdm(5, 1) + @testset "x with length $N, y with length $M" for (N, M) in ((2, 3), (0, 0), (0, 3)) + x, y = randn(rng, T, N), randn(rng, T, M) + z̄ = randn(rng, T, N + M) + xy = vcat(x, y) + x̄ȳ_manual = j′vp(fdm, xy->sin.(xy), z̄, xy)[1] + x̄ȳ_auto = j′vp(fdm, x->sin.(vcat(x[1], x[2])), z̄, (x, y))[1] + x̄ȳ_multi = j′vp(fdm, (x, y)->sin.(vcat(x, y)), z̄, x, y) + @test x̄ȳ_manual ≈ vcat(x̄ȳ_auto...) + @test x̄ȳ_manual ≈ vcat(x̄ȳ_multi...) + end end # Tests for complex numbers, to prevent regressions against