From 1889f7d60b9a94f3e23d24120f2b13d26d06ea9a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Th=C3=A9o=20Galy-Fajou?= Date: Tue, 25 Oct 2022 17:15:32 +0200 Subject: [PATCH 01/14] Stable version of product and test --- src/kernels/kernelproduct.jl | 5 ++++- test/kernels/kernelproduct.jl | 4 ++++ 2 files changed, 8 insertions(+), 1 deletion(-) diff --git a/src/kernels/kernelproduct.jl b/src/kernels/kernelproduct.jl index 990b4a1bb..c95c1126e 100644 --- a/src/kernels/kernelproduct.jl +++ b/src/kernels/kernelproduct.jl @@ -45,8 +45,11 @@ Base.length(k::KernelProduct) = length(k.kernels) (κ::KernelProduct)(x, y) = prod(k(x, y) for k in κ.kernels) +_hadamard(f::Tf, x::Tuple) where {Tf} = f(first(x)) .* _hadamard(f, Base.tail(x)) +_hadamard(f::Tf, x::Tuple{Tx}) where {Tf,Tx} = f(only(x)) + function kernelmatrix(κ::KernelProduct, x::AbstractVector) - return reduce(hadamard, kernelmatrix(k, x) for k in κ.kernels) + return _hadamard(Base.Fix2(kernelmatrix, x), κ.kernels) end function kernelmatrix(κ::KernelProduct, x::AbstractVector, y::AbstractVector) diff --git a/test/kernels/kernelproduct.jl b/test/kernels/kernelproduct.jl index 1c50d52d9..a05da5f91 100644 --- a/test/kernels/kernelproduct.jl +++ b/test/kernels/kernelproduct.jl @@ -19,4 +19,8 @@ KernelProduct(SqExponentialKernel(), LinearKernel(; c=c)) end test_params(k1 * k2, (k1, k2)) + + nested_k = RBFKernel() * ((LinearKernel() + CosineKernel() * RBFKernel()) ∘ SelectTransform(1)) + x = RowVecs(rand(10, 2)) + @test (@inferred kernelmatrix(nested_k, x)) isa Matrix{Float64} end From 530fce700251f78be5899128da6a80cd75ffc8dd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Th=C3=A9o=20Galy-Fajou?= Date: Tue, 25 Oct 2022 17:44:14 +0200 Subject: [PATCH 02/14] Cleanup --- src/kernels/kernelproduct.jl | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/kernels/kernelproduct.jl b/src/kernels/kernelproduct.jl index c95c1126e..fa4c40b4a 100644 --- a/src/kernels/kernelproduct.jl +++ b/src/kernels/kernelproduct.jl @@ -45,11 +45,11 @@ Base.length(k::KernelProduct) = length(k.kernels) (κ::KernelProduct)(x, y) = prod(k(x, y) for k in κ.kernels) -_hadamard(f::Tf, x::Tuple) where {Tf} = f(first(x)) .* _hadamard(f, Base.tail(x)) -_hadamard(f::Tf, x::Tuple{Tx}) where {Tf,Tx} = f(only(x)) +_hadamard(f, ks::Tuple, x) = f(first(ks), x) .* _hadamard(f, Base.tail(ks), x) +_hadamard(f, ks::Tuple{Tx}, x) where {Tx} = f(only(ks), x) function kernelmatrix(κ::KernelProduct, x::AbstractVector) - return _hadamard(Base.Fix2(kernelmatrix, x), κ.kernels) + return _hadamard(kernelmatrix, κ.kernels, x) end function kernelmatrix(κ::KernelProduct, x::AbstractVector, y::AbstractVector) From 8de3e73404a21a52b73c7b8d6dbfeb0a157bebcd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Th=C3=A9o=20Galy-Fajou?= Date: Tue, 25 Oct 2022 17:48:16 +0200 Subject: [PATCH 03/14] Update test/kernels/kernelproduct.jl Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com> --- test/kernels/kernelproduct.jl | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/test/kernels/kernelproduct.jl b/test/kernels/kernelproduct.jl index a05da5f91..10bb8276f 100644 --- a/test/kernels/kernelproduct.jl +++ b/test/kernels/kernelproduct.jl @@ -20,7 +20,8 @@ end test_params(k1 * k2, (k1, k2)) - nested_k = RBFKernel() * ((LinearKernel() + CosineKernel() * RBFKernel()) ∘ SelectTransform(1)) + nested_k = + RBFKernel() * ((LinearKernel() + CosineKernel() * RBFKernel()) ∘ SelectTransform(1)) x = RowVecs(rand(10, 2)) @test (@inferred kernelmatrix(nested_k, x)) isa Matrix{Float64} end From e92e14fcce550b58bc615cf64456be53e5e27bba Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Th=C3=A9o=20Galy-Fajou?= Date: Tue, 25 Oct 2022 18:04:02 +0200 Subject: [PATCH 04/14] Bump version --- Project.toml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Project.toml b/Project.toml index 4b68161dd..591d1f6ad 100644 --- a/Project.toml +++ b/Project.toml @@ -1,6 +1,6 @@ name = "KernelFunctions" uuid = "ec8451be-7e33-11e9-00cf-bbf324bd1392" -version = "0.10.48" +version = "0.10.49" [deps] ChainRulesCore = "d360d2e6-b24c-11e9-a2a3-2a2ae2dbcce4" From 68bde159f1380194c1cb6f63a514ee3207dd1751 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Th=C3=A9o=20Galy-Fajou?= Date: Sat, 29 Oct 2022 16:35:16 +0200 Subject: [PATCH 05/14] Generalize approach to all functions --- src/kernels/kernelproduct.jl | 10 ++++++---- src/kernels/kernelsum.jl | 12 ++++++------ 2 files changed, 12 insertions(+), 10 deletions(-) diff --git a/src/kernels/kernelproduct.jl b/src/kernels/kernelproduct.jl index fa4c40b4a..ce54b37b3 100644 --- a/src/kernels/kernelproduct.jl +++ b/src/kernels/kernelproduct.jl @@ -45,19 +45,21 @@ Base.length(k::KernelProduct) = length(k.kernels) (κ::KernelProduct)(x, y) = prod(k(x, y) for k in κ.kernels) -_hadamard(f, ks::Tuple, x) = f(first(ks), x) .* _hadamard(f, Base.tail(ks), x) -_hadamard(f, ks::Tuple{Tx}, x) where {Tx} = f(only(ks), x) +_hadamard(f, ks::Tuple, args...) = f(first(ks), args...) .* _hadamard(f, Base.tail(ks), args...) +_hadamard(f, ks::Tuple{Tx}, args...) where {Tx} = f(only(ks), args...) + +(κ::KernelProduct)(x, y) = _hadamard((k, x, y) -> k(x, y), κ.kernels, x, y) function kernelmatrix(κ::KernelProduct, x::AbstractVector) return _hadamard(kernelmatrix, κ.kernels, x) end function kernelmatrix(κ::KernelProduct, x::AbstractVector, y::AbstractVector) - return reduce(hadamard, kernelmatrix(k, x, y) for k in κ.kernels) + return _hadamard(kernelmatrix, κ.kernels, x, y) end function kernelmatrix_diag(κ::KernelProduct, x::AbstractVector) - return reduce(hadamard, kernelmatrix_diag(k, x) for k in κ.kernels) + return _hadamard(kernelmatrix_diag, κ.kernels, x, y) end function kernelmatrix_diag(κ::KernelProduct, x::AbstractVector, y::AbstractVector) diff --git a/src/kernels/kernelsum.jl b/src/kernels/kernelsum.jl index 2ca25370c..29966cb12 100644 --- a/src/kernels/kernelsum.jl +++ b/src/kernels/kernelsum.jl @@ -43,21 +43,21 @@ end Base.length(k::KernelSum) = length(k.kernels) -_sum(f::Tf, x::Tuple) where {Tf} = f(x[1]) + _sum(f, Base.tail(x)) -_sum(f::Tf, x::Tuple{Tx}) where {Tf,Tx} = f(x[1]) +_sum(f, ks::Tuple, args...) = f(first(ks), args...) + _sum(f, Base.tail(ks). args...) +_sum(f, ks::Tuple{Tx}, args...) where {Tx} = f(only(ks), args...) -(κ::KernelSum)(x, y) = _sum(k -> k(x, y), κ.kernels) +(κ::KernelSum)(x, y) = _sum((k, x, y) -> k(x, y), κ.kernels, x, y) function kernelmatrix(κ::KernelSum, x::AbstractVector) - return _sum(Base.Fix2(kernelmatrix, x), κ.kernels) + return _sum(kernelmatrix, κ.kernels, x) end function kernelmatrix(κ::KernelSum, x::AbstractVector, y::AbstractVector) - return _sum(k -> kernelmatrix(k, x, y), κ.kernels) + return _sum(kernelmatrix, κ.kernels, x, y) end function kernelmatrix_diag(κ::KernelSum, x::AbstractVector) - return _sum(Base.Fix2(kernelmatrix_diag, x), κ.kernels) + return _sum(k -> kernelmatrix_diag(k, x), κ.kernels) end function kernelmatrix_diag(κ::KernelSum, x::AbstractVector, y::AbstractVector) From ff2ec8853ba5fa888f36e13beeac592ed3997cc6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Th=C3=A9o=20Galy-Fajou?= Date: Sat, 29 Oct 2022 18:15:49 +0200 Subject: [PATCH 06/14] Refactor TestUtils --- src/TestUtils.jl | 150 ++++++++++++++++++++++------------ src/kernels/kernelproduct.jl | 4 +- src/kernels/kernelsum.jl | 2 +- test/kernels/kernelproduct.jl | 10 +-- test/kernels/kernelsum.jl | 39 ++++----- test/runtests.jl | 2 +- 6 files changed, 120 insertions(+), 87 deletions(-) diff --git a/src/TestUtils.jl b/src/TestUtils.jl index 357375dbf..b746e7433 100644 --- a/src/TestUtils.jl +++ b/src/TestUtils.jl @@ -86,18 +86,94 @@ function test_interface( @test kernelmatrix_diag!(tmp_diag, k, x0, x1) ≈ kernelmatrix_diag(k, x0, x1) end -function test_interface( - rng::AbstractRNG, k::Kernel, ::Type{Vector{T}}; kwargs... + +""" + test_interface([rng::AbstractRNG], k::Kernel, ::Type{T}=Float64; kwargs...) where {T} + +Run the [`test_interface`](@ref) tests for randomly generated inputs of types `Vector{T}`, +`Vector{Vector{T}}`, `ColVecs{T}`, and `RowVecs{T}`. + +For other input types, please provide the data manually. + +The keyword arguments are forwarded to the invocations of [`test_interface`](@ref) with the +randomly generated inputs. +""" +function test_interface(k::Kernel, T::Type=Float64; kwargs...) + return test_interface(Random.GLOBAL_RNG, k, T; kwargs...) +end + +function test_interface(rng::AbstractRNG, k::Kernel, T::Type=Float64; kwargs...) + return test_with_type(test_interface, rng, k, T; kwargs...) +end + +""" +test_type_stability( + k::Kernel, + x0::AbstractVector, + x1::AbstractVector, + x2::AbstractVector +) + +Run type stability checks over `k(x,y)` and the different functions of the API (`kernelmatrix`, `kernelmatrix_diag`). +`x0` and `x1` should be of the same length with different values, while `x0` and `x2` should be of different lengths. +""" +function test_type_stability(k::Kernel, x0::AbstractVector, x1::AbstractVector, x2::AbstractVector) + # Ensure that we have the required inputs. + @assert length(x0) == length(x1) + @assert length(x0) ≠ length(x2) + # @test @inferred(k(first(x0), first(x1))) isa Real + @test @inferred(kernelmatrix(k, x0)) isa AbstractMatrix + @test @inferred(kernelmatrix(k, x0, x2)) isa AbstractMatrix + @test @inferred(kernelmatrix_diag(k, x0)) isa AbstractVector + @test @inferred(kernelmatrix_diag(k, x0, x1)) isa AbstractVector +end + +function test_type_stability(k::Kernel, ::Type{T}=Float64; kwargs...) where {T} + return test_type_stability(Random.GLOBAL_RNG, k, T; kwargs...) +end + +function test_type_stability(rng::AbstractRNG, k::Kernel, ::Type{T}; kwargs...) where {T} + return test_with_type(test_type_stability, rng, k, T; kwargs...) +end + +""" + test_with_type(f, rng::AbstractRNG, k::Kernel, ::Type{T}; kwargs...) where {T<:Real} + +Run the functions `f`, (for example [`test_interface`](@ref) or [`test_type_stable`](@ref)) for randomly generated inputs of types `Vector{T}`, +`Vector{Vector{T}}`, `ColVecs{T}`, and `RowVecs{T}`. + +For other input types, please provide the data manually. + +The keyword arguments are forwarded to the invocations of `f` with the +randomly generated inputs. +""" +function test_with_type(f, rng::AbstractRNG, k::Kernel, ::Type{T}; kwargs...) where {T} + @testset "Vector{$T}" begin + test_with_type(f, rng, k, Vector{T}; kwargs...) + end + @testset "ColVecs{$T}" begin + test_with_type(f, rng, k, ColVecs{T}; kwargs...) + end + @testset "RowVecs{$T}" begin + test_with_type(f, rng, k, RowVecs{T}; kwargs...) + end + @testset "Vector{Vector{$T}}" begin + test_with_type(f, rng, k, Vector{Vector{T}}; kwargs...) + end +end + +function test_with_type( + f, rng::AbstractRNG, k::Kernel, ::Type{Vector{T}}; kwargs... ) where {T<:Real} - return test_interface( + return f( k, randn(rng, T, 11), randn(rng, T, 11), randn(rng, T, 13); kwargs... ) end -function test_interface( - rng::AbstractRNG, k::MOKernel, ::Type{Vector{Tuple{T,Int}}}; dim_out=3, kwargs... +function test_with_type( + f, rng::AbstractRNG, k::MOKernel, ::Type{Vector{Tuple{T,Int}}}; dim_out=3, kwargs... ) where {T<:Real} - return test_interface( + return f( k, [(randn(rng, T), rand(rng, 1:dim_out)) for i in 1:11], [(randn(rng, T), rand(rng, 1:dim_out)) for i in 1:11], @@ -106,10 +182,10 @@ function test_interface( ) end -function test_interface( - rng::AbstractRNG, k::Kernel, ::Type{<:ColVecs{T}}; dim_in=2, kwargs... +function test_with_type( + f, rng::AbstractRNG, k::Kernel, ::Type{<:ColVecs{T}}; dim_in=2, kwargs... ) where {T<:Real} - return test_interface( + return f( k, ColVecs(randn(rng, T, dim_in, 11)), ColVecs(randn(rng, T, dim_in, 11)), @@ -118,10 +194,10 @@ function test_interface( ) end -function test_interface( - rng::AbstractRNG, k::Kernel, ::Type{<:RowVecs{T}}; dim_in=2, kwargs... +function test_with_type( + f, rng::AbstractRNG, k::Kernel, ::Type{<:RowVecs{T}}; dim_in=2, kwargs... ) where {T<:Real} - return test_interface( + return f( k, RowVecs(randn(rng, T, 11, dim_in)), RowVecs(randn(rng, T, 11, dim_in)), @@ -130,10 +206,10 @@ function test_interface( ) end -function test_interface( - rng::AbstractRNG, k::Kernel, ::Type{<:Vector{Vector{T}}}; dim_in=2, kwargs... +function test_with_type( + f, rng::AbstractRNG, k::Kernel, ::Type{<:Vector{Vector{T}}}; dim_in=2, kwargs... ) where {T<:Real} - return test_interface( + return f( k, [randn(rng, T, dim_in) for _ in 1:11], [randn(rng, T, dim_in) for _ in 1:11], @@ -142,8 +218,8 @@ function test_interface( ) end -function test_interface(rng::AbstractRNG, k::Kernel, ::Type{Vector{String}}; kwargs...) - return test_interface( +function test_with_type(f, rng::AbstractRNG, k::Kernel, ::Type{Vector{String}}; kwargs...) + return f( k, [randstring(rng) for _ in 1:3], [randstring(rng) for _ in 1:3], @@ -152,10 +228,10 @@ function test_interface(rng::AbstractRNG, k::Kernel, ::Type{Vector{String}}; kwa ) end -function test_interface( - rng::AbstractRNG, k::Kernel, ::Type{ColVecs{String}}; dim_in=2, kwargs... +function test_with_type( + f, rng::AbstractRNG, k::Kernel, ::Type{ColVecs{String}}; dim_in=2, kwargs... ) - return test_interface( + return f( k, ColVecs([randstring(rng) for _ in 1:dim_in, _ in 1:3]), ColVecs([randstring(rng) for _ in 1:dim_in, _ in 1:3]), @@ -164,38 +240,8 @@ function test_interface( ) end -function test_interface(k::Kernel, T::Type{<:AbstractVector}; kwargs...) - return test_interface(Random.GLOBAL_RNG, k, T; kwargs...) -end - -""" - test_interface([rng::AbstractRNG], k::Kernel, ::Type{T}; kwargs...) where {T<:Real} - -Run the [`test_interface`](@ref) tests for randomly generated inputs of types `Vector{T}`, -`Vector{Vector{T}}`, `ColVecs{T}`, and `RowVecs{T}`. - -For other input types, please provide the data manually. - -The keyword arguments are forwarded to the invocations of [`test_interface`](@ref) with the -randomly generated inputs. -""" -function test_interface(rng::AbstractRNG, k::Kernel, ::Type{T}; kwargs...) where {T<:Real} - @testset "Vector{$T}" begin - test_interface(rng, k, Vector{T}; kwargs...) - end - @testset "ColVecs{$T}" begin - test_interface(rng, k, ColVecs{T}; kwargs...) - end - @testset "RowVecs{$T}" begin - test_interface(rng, k, RowVecs{T}; kwargs...) - end - @testset "Vector{Vector{T}}" begin - test_interface(rng, k, Vector{Vector{T}}; kwargs...) - end -end - -function test_interface(k::Kernel, T::Type{<:Real}=Float64; kwargs...) - return test_interface(Random.GLOBAL_RNG, k, T; kwargs...) +function test_with_type(f, k::Kernel, T::Type{<:Real}; kwargs...) + return test_with_type(f, Random.GLOBAL_RNG, k, T; kwargs...) end """ diff --git a/src/kernels/kernelproduct.jl b/src/kernels/kernelproduct.jl index ce54b37b3..7a42725fe 100644 --- a/src/kernels/kernelproduct.jl +++ b/src/kernels/kernelproduct.jl @@ -59,11 +59,11 @@ function kernelmatrix(κ::KernelProduct, x::AbstractVector, y::AbstractVector) end function kernelmatrix_diag(κ::KernelProduct, x::AbstractVector) - return _hadamard(kernelmatrix_diag, κ.kernels, x, y) + return _hadamard(kernelmatrix_diag, κ.kernels, x) end function kernelmatrix_diag(κ::KernelProduct, x::AbstractVector, y::AbstractVector) - return reduce(hadamard, kernelmatrix_diag(k, x, y) for k in κ.kernels) + return _hadamard(kernelmatrix_diag, κ.kernels, x, y) end function Base.show(io::IO, κ::KernelProduct) diff --git a/src/kernels/kernelsum.jl b/src/kernels/kernelsum.jl index 29966cb12..51199b3e8 100644 --- a/src/kernels/kernelsum.jl +++ b/src/kernels/kernelsum.jl @@ -43,7 +43,7 @@ end Base.length(k::KernelSum) = length(k.kernels) -_sum(f, ks::Tuple, args...) = f(first(ks), args...) + _sum(f, Base.tail(ks). args...) +_sum(f, ks::Tuple, args...) = f(first(ks), args...) + _sum(f, Base.tail(ks), args...) _sum(f, ks::Tuple{Tx}, args...) where {Tx} = f(only(ks), args...) (κ::KernelSum)(x, y) = _sum((k, x, y) -> k(x, y), κ.kernels, x, y) diff --git a/test/kernels/kernelproduct.jl b/test/kernels/kernelproduct.jl index 10bb8276f..b2cdea042 100644 --- a/test/kernels/kernelproduct.jl +++ b/test/kernels/kernelproduct.jl @@ -10,8 +10,8 @@ ) # Standardised tests. - TestUtils.test_interface(k, Float64) - TestUtils.test_interface(ConstantKernel(; c=1.0) * WhiteKernel(), Vector{String}) + test_interface(k, Float64) + test_interface(ConstantKernel(; c=1.0) * WhiteKernel(), Vector{String}) test_ADs( x -> KernelProduct(SqExponentialKernel(), LinearKernel(; c=exp(x[1]))), rand(1) ) @@ -20,8 +20,6 @@ end test_params(k1 * k2, (k1, k2)) - nested_k = - RBFKernel() * ((LinearKernel() + CosineKernel() * RBFKernel()) ∘ SelectTransform(1)) - x = RowVecs(rand(10, 2)) - @test (@inferred kernelmatrix(nested_k, x)) isa Matrix{Float64} + nested_k = RBFKernel() * (LinearKernel() + CosineKernel() * RBFKernel()) + test_type_stability(nested_k) end diff --git a/test/kernels/kernelsum.jl b/test/kernels/kernelsum.jl index 716343ef7..11ae1dcd2 100644 --- a/test/kernels/kernelsum.jl +++ b/test/kernels/kernelsum.jl @@ -4,39 +4,28 @@ k = KernelSum(k1, k2) @test k == KernelSum([k1, k2]) == KernelSum((k1, k2)) @test length(k) == 2 - @test string(k) == ( + @test repr(k) == ( "Sum of 2 kernels:\n" * "\tLinear Kernel (c = 0.0)\n" * "\tSquared Exponential Kernel (metric = Euclidean(0.0))" ) # Standardised tests. - TestUtils.test_interface(k, Float64) - TestUtils.test_interface(ConstantKernel(; c=1.5) * WhiteKernel(), Vector{String}) - test_ADs(x -> KernelSum(SqExponentialKernel(), LinearKernel(; c=exp(x[1]))), rand(1)) - test_interface_ad_perf(2.4, StableRNG(123456)) do c - KernelSum(SqExponentialKernel(), LinearKernel(; c=c)) - end + test_interface(k, Float64) + test_interface(ConstantKernel(; c=1.5) + WhiteKernel(), Vector{String}) + # test_ADs(x -> KernelSum(SqExponentialKernel(), LinearKernel(; c=exp(x[1]))), rand(1)) + # test_interface_ad_perf(2.4, StableRNG(123456)) do c + # KernelSum(SqExponentialKernel(), LinearKernel(; c=c)) + # end - test_params(k1 + k2, (k1, k2)) + # test_params(k1 + k2, (k1, k2)) # Regression tests for https://github.com//issues/458 - @testset "Type stability" begin - function check_type_stability(k) - @test (@inferred k(0.1, 0.2)) isa Real - x = rand(10) - y = rand(10) - @test (@inferred kernelmatrix(k, x)) isa Matrix{<:Real} - @test (@inferred kernelmatrix(k, x, y)) isa Matrix{<:Real} - @test (@inferred kernelmatrix_diag(k, x)) isa Vector{<:Real} - @test (@inferred kernelmatrix_diag(k, x, y)) isa Vector{<:Real} - end - @testset for k in ( - RBFKernel() + RBFKernel() * LinearKernel(), - RBFKernel() + RBFKernel() * ExponentialKernel(), - RBFKernel() * (LinearKernel() + ExponentialKernel()), - ) - check_type_stability(k) - end + @testset for k in ( + RBFKernel() + RBFKernel() * LinearKernel(), + RBFKernel() + RBFKernel() * ExponentialKernel(), + RBFKernel() * (LinearKernel() + ExponentialKernel()), + ) + test_type_stability(k) end end diff --git a/test/runtests.jl b/test/runtests.jl index dd6eb2d8a..0fe962648 100644 --- a/test/runtests.jl +++ b/test/runtests.jl @@ -20,7 +20,7 @@ using Compat: only using KernelFunctions: SimpleKernel, metric, kappa, ColVecs, RowVecs, TestUtils -using KernelFunctions.TestUtils: test_interface, example_inputs +using KernelFunctions.TestUtils: test_interface, test_type_stability, example_inputs # The GROUP is used to run different sets of tests in parallel on the GitHub Actions CI. # If you want to introduce a new group, ensure you also add it to .github/workflows/ci.yml From 6bcd8cd8f906f1c2e0d636ef9538f8c6ad9e3dab Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Th=C3=A9o=20Galy-Fajou?= Date: Sat, 29 Oct 2022 18:17:04 +0200 Subject: [PATCH 07/14] Uncomment tests --- test/kernels/kernelsum.jl | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/test/kernels/kernelsum.jl b/test/kernels/kernelsum.jl index 11ae1dcd2..cfe239717 100644 --- a/test/kernels/kernelsum.jl +++ b/test/kernels/kernelsum.jl @@ -13,12 +13,12 @@ # Standardised tests. test_interface(k, Float64) test_interface(ConstantKernel(; c=1.5) + WhiteKernel(), Vector{String}) - # test_ADs(x -> KernelSum(SqExponentialKernel(), LinearKernel(; c=exp(x[1]))), rand(1)) - # test_interface_ad_perf(2.4, StableRNG(123456)) do c - # KernelSum(SqExponentialKernel(), LinearKernel(; c=c)) - # end + test_ADs(x -> KernelSum(SqExponentialKernel(), LinearKernel(; c=exp(x[1]))), rand(1)) + test_interface_ad_perf(2.4, StableRNG(123456)) do c + KernelSum(SqExponentialKernel(), LinearKernel(; c=c)) + end - # test_params(k1 + k2, (k1, k2)) + test_params(k1 + k2, (k1, k2)) # Regression tests for https://github.com//issues/458 @testset for k in ( From 1baa148576dddccdb5b36f691a75897562bd8b3c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Th=C3=A9o=20Galy-Fajou?= Date: Sat, 29 Oct 2022 18:17:41 +0200 Subject: [PATCH 08/14] Update src/TestUtils.jl Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com> --- src/TestUtils.jl | 1 - 1 file changed, 1 deletion(-) diff --git a/src/TestUtils.jl b/src/TestUtils.jl index b746e7433..811e3e461 100644 --- a/src/TestUtils.jl +++ b/src/TestUtils.jl @@ -86,7 +86,6 @@ function test_interface( @test kernelmatrix_diag!(tmp_diag, k, x0, x1) ≈ kernelmatrix_diag(k, x0, x1) end - """ test_interface([rng::AbstractRNG], k::Kernel, ::Type{T}=Float64; kwargs...) where {T} From 2bb2c5d370c44ccb8bfe534620d5f7fe053bb4e4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Th=C3=A9o=20Galy-Fajou?= Date: Sat, 29 Oct 2022 18:17:51 +0200 Subject: [PATCH 09/14] Update src/kernels/kernelproduct.jl Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com> --- src/kernels/kernelproduct.jl | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/kernels/kernelproduct.jl b/src/kernels/kernelproduct.jl index 7a42725fe..a99a455f8 100644 --- a/src/kernels/kernelproduct.jl +++ b/src/kernels/kernelproduct.jl @@ -45,7 +45,9 @@ Base.length(k::KernelProduct) = length(k.kernels) (κ::KernelProduct)(x, y) = prod(k(x, y) for k in κ.kernels) -_hadamard(f, ks::Tuple, args...) = f(first(ks), args...) .* _hadamard(f, Base.tail(ks), args...) +function _hadamard(f, ks::Tuple, args...) + return f(first(ks), args...) .* _hadamard(f, Base.tail(ks), args...) +end _hadamard(f, ks::Tuple{Tx}, args...) where {Tx} = f(only(ks), args...) (κ::KernelProduct)(x, y) = _hadamard((k, x, y) -> k(x, y), κ.kernels, x, y) From e32c368e01a77dc7bb5f54e4002a4f08c96f1abc Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Th=C3=A9o=20Galy-Fajou?= Date: Sat, 29 Oct 2022 18:18:09 +0200 Subject: [PATCH 10/14] Update src/TestUtils.jl Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com> --- src/TestUtils.jl | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/src/TestUtils.jl b/src/TestUtils.jl index 811e3e461..293a7bed0 100644 --- a/src/TestUtils.jl +++ b/src/TestUtils.jl @@ -164,9 +164,7 @@ end function test_with_type( f, rng::AbstractRNG, k::Kernel, ::Type{Vector{T}}; kwargs... ) where {T<:Real} - return f( - k, randn(rng, T, 11), randn(rng, T, 11), randn(rng, T, 13); kwargs... - ) + return f(k, randn(rng, T, 11), randn(rng, T, 11), randn(rng, T, 13); kwargs...) end function test_with_type( From 9401778e240fddbec0ebe0136346cb63ee1a1097 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Th=C3=A9o=20Galy-Fajou?= Date: Sat, 29 Oct 2022 18:18:21 +0200 Subject: [PATCH 11/14] Update src/TestUtils.jl Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com> --- src/TestUtils.jl | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/TestUtils.jl b/src/TestUtils.jl index 293a7bed0..f898e9079 100644 --- a/src/TestUtils.jl +++ b/src/TestUtils.jl @@ -116,7 +116,9 @@ test_type_stability( Run type stability checks over `k(x,y)` and the different functions of the API (`kernelmatrix`, `kernelmatrix_diag`). `x0` and `x1` should be of the same length with different values, while `x0` and `x2` should be of different lengths. """ -function test_type_stability(k::Kernel, x0::AbstractVector, x1::AbstractVector, x2::AbstractVector) +function test_type_stability( + k::Kernel, x0::AbstractVector, x1::AbstractVector, x2::AbstractVector +) # Ensure that we have the required inputs. @assert length(x0) == length(x1) @assert length(x0) ≠ length(x2) From 25798dc4864155e7cecb6a73f6a35fd32e5dd8ba Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Th=C3=A9o=20Galy-Fajou?= Date: Tue, 1 Nov 2022 13:14:08 +0100 Subject: [PATCH 12/14] Fix formatting and missing definition in kernel sum --- src/TestUtils.jl | 18 +++++++++--------- src/kernels/kernelsum.jl | 5 +++-- 2 files changed, 12 insertions(+), 11 deletions(-) diff --git a/src/TestUtils.jl b/src/TestUtils.jl index f898e9079..b76b8279a 100644 --- a/src/TestUtils.jl +++ b/src/TestUtils.jl @@ -106,15 +106,16 @@ function test_interface(rng::AbstractRNG, k::Kernel, T::Type=Float64; kwargs...) end """ -test_type_stability( - k::Kernel, - x0::AbstractVector, - x1::AbstractVector, - x2::AbstractVector -) + test_type_stability( + k::Kernel, + x0::AbstractVector, + x1::AbstractVector, + x2::AbstractVector, + ) -Run type stability checks over `k(x,y)` and the different functions of the API (`kernelmatrix`, `kernelmatrix_diag`). -`x0` and `x1` should be of the same length with different values, while `x0` and `x2` should be of different lengths. +Run type stability checks over `k(x,y)` and the different functions of the API +(`kernelmatrix`, `kernelmatrix_diag`). `x0` and `x1` should be of the same +length with different values, while `x0` and `x2` should be of different lengths. """ function test_type_stability( k::Kernel, x0::AbstractVector, x1::AbstractVector, x2::AbstractVector @@ -122,7 +123,6 @@ function test_type_stability( # Ensure that we have the required inputs. @assert length(x0) == length(x1) @assert length(x0) ≠ length(x2) - # @test @inferred(k(first(x0), first(x1))) isa Real @test @inferred(kernelmatrix(k, x0)) isa AbstractMatrix @test @inferred(kernelmatrix(k, x0, x2)) isa AbstractMatrix @test @inferred(kernelmatrix_diag(k, x0)) isa AbstractVector diff --git a/src/kernels/kernelsum.jl b/src/kernels/kernelsum.jl index 51199b3e8..3b0f1b5cd 100644 --- a/src/kernels/kernelsum.jl +++ b/src/kernels/kernelsum.jl @@ -48,6 +48,7 @@ _sum(f, ks::Tuple{Tx}, args...) where {Tx} = f(only(ks), args...) (κ::KernelSum)(x, y) = _sum((k, x, y) -> k(x, y), κ.kernels, x, y) + function kernelmatrix(κ::KernelSum, x::AbstractVector) return _sum(kernelmatrix, κ.kernels, x) end @@ -57,11 +58,11 @@ function kernelmatrix(κ::KernelSum, x::AbstractVector, y::AbstractVector) end function kernelmatrix_diag(κ::KernelSum, x::AbstractVector) - return _sum(k -> kernelmatrix_diag(k, x), κ.kernels) + return _sum(kernelmatrix_diag, κ.kernels, x) end function kernelmatrix_diag(κ::KernelSum, x::AbstractVector, y::AbstractVector) - return _sum(k -> kernelmatrix_diag(k, x, y), κ.kernels) + return _sum(kernelmatrix_diag, κ.kernels, x, y) end function Base.show(io::IO, κ::KernelSum) From ecd055658775f6a6eab49df2d3cc3a38a71d622c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Th=C3=A9o=20Galy-Fajou?= Date: Tue, 1 Nov 2022 13:15:31 +0100 Subject: [PATCH 13/14] Additional formatting --- src/TestUtils.jl | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/src/TestUtils.jl b/src/TestUtils.jl index b76b8279a..cd14ec718 100644 --- a/src/TestUtils.jl +++ b/src/TestUtils.jl @@ -138,9 +138,10 @@ function test_type_stability(rng::AbstractRNG, k::Kernel, ::Type{T}; kwargs...) end """ - test_with_type(f, rng::AbstractRNG, k::Kernel, ::Type{T}; kwargs...) where {T<:Real} + test_with_type(f, rng::AbstractRNG, k::Kernel, ::Type{T}; kwargs...) where {T} -Run the functions `f`, (for example [`test_interface`](@ref) or [`test_type_stable`](@ref)) for randomly generated inputs of types `Vector{T}`, +Run the functions `f`, (for example [`test_interface`](@ref) or +[`test_type_stable`](@ref)) for randomly generated inputs of types `Vector{T}`, `Vector{Vector{T}}`, `ColVecs{T}`, and `RowVecs{T}`. For other input types, please provide the data manually. From f647b40eebf97aa058f679f8758429ffa2c15cec Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Th=C3=A9o=20Galy-Fajou?= Date: Tue, 1 Nov 2022 13:16:16 +0100 Subject: [PATCH 14/14] Moar formatting --- src/kernels/kernelsum.jl | 1 - 1 file changed, 1 deletion(-) diff --git a/src/kernels/kernelsum.jl b/src/kernels/kernelsum.jl index 3b0f1b5cd..77709502c 100644 --- a/src/kernels/kernelsum.jl +++ b/src/kernels/kernelsum.jl @@ -48,7 +48,6 @@ _sum(f, ks::Tuple{Tx}, args...) where {Tx} = f(only(ks), args...) (κ::KernelSum)(x, y) = _sum((k, x, y) -> k(x, y), κ.kernels, x, y) - function kernelmatrix(κ::KernelSum, x::AbstractVector) return _sum(kernelmatrix, κ.kernels, x) end