1+ using Chairmarks
12using BenchmarkTools
23using Copulas
34using StatsBase
45using Distributions
56using StableRNGs
6- const rng = StableRNG (123 )
77
8- # PkgBenchmark entrypoint; must define SUITE
9- const SUITE = BenchmarkGroup ()
10-
11-
12- const EXAMPLES = unique ([
13- # AMH: keep one non-2D representative
14- AMHCopula (3 , 0.6 ),
15-
16- # Archimax: cover each generator family and each tail type at least once (no full cartesian product)
17- ArchimaxCopula (2 , Copulas. BB1Generator (1.3 , 1.4 ), Copulas. GalambosTail (0.7 )),
18- ArchimaxCopula (2 , Copulas. ClaytonGenerator (1.5 ), Copulas. HuslerReissTail (0.6 )),
19- ArchimaxCopula (2 , Copulas. FrankGenerator (6.0 ), Copulas. LogTail (1.5 )),
20- ArchimaxCopula (2 , Copulas. GumbelGenerator (2.0 ), Copulas. AsymGalambosTail (0.35 , 0.65 , 0.3 )),
21- ArchimaxCopula (2 , Copulas. JoeGenerator (2.5 ), Copulas. GalambosTail (2.5 )),
22-
23- # Archimedean: one empirical generator (non-2D)
24- ArchimedeanCopula (3 , EmpiricalGenerator (randn (rng, 3 , 200 ))),
25-
26- # Asymmetric families: one representative each
27- AsymGalambosCopula (2 , 5.0 , 0.8 , 0.3 ),
28- AsymLogCopula (2 , 1.5 , 0.5 , 0.2 ),
29- AsymMixedCopula (2 , 0.12 , 0.13 ),
30-
31- # BB families: one per family
32- BB10Copula (2 , 3.0 , 0.8 ),
33- BB1Copula (2 , 1.2 , 1.5 ),
34- BB2Copula (2 , 1.5 , 1.8 ),
35- BB3Copula (2 , 2.5 , 0.5 ),
36- BB6Copula (2 , 1.5 , 1.4 ),
37- BB7Copula (2 , 1.5 , 0.4 ),
38- BB8Copula (2 , 1.5 , 0.6 ),
39- BB9Copula (2 , 2.0 , 1.5 ),
40-
41- # BC2: symmetric and asymmetric
42- BC2Copula (2 , 0.5 , 0.5 ),
43- BC2Copula (2 , 0.7 , 0.3 ),
44-
45- # Bernstein copulas: a couple of bases
46- BernsteinCopula (ClaytonCopula (3 , 3.3 ); m= 5 ),
47- BernsteinCopula (randn (rng, 3 ,100 ); m= 5 , pseudo_values= false ),
48-
49- # Beta & Checkerboard: prefer non-2D where available
50- BetaCopula (randn (rng, 3 ,100 )),
51- CheckerboardCopula (randn (rng, 3 ,100 ); pseudo_values= false ),
52-
53- # Clayton: keep one negative and one positive; plus one non-2D
54- ClaytonCopula (2 , - 0.7 ),
55- ClaytonCopula (4 , 3.0 ),
56-
57- # Subset copula
58- Copulas. SubsetCopula (RafteryCopula (3 , 0.5 ), (2 ,1 )),
59-
60- # Cuadras-Auge: two extremes
61- CuadrasAugeCopula (2 , 0.0 ),
62- CuadrasAugeCopula (2 , 0.8 ),
63-
64- # Empirical copulas
65- EmpiricalCopula (randn (2 ,20 ), pseudo_values= false ),
66- EmpiricalEVCopula (randn (rng, 2 ,20 ); method= :pickands , pseudo_values= false ),
67-
68- # FGM: one 2D max and one 3D vector case
69- FGMCopula (2 , 1 ),
70- FGMCopula (3 , [0.1 ,0.2 ,0.3 ,0.4 ]),
71-
72- # Frank: negative and positive, with a non-2D example
73- FrankCopula (2 , - 5 ),
74- FrankCopula (4 , 30 ),
75-
76- # Galambos: small and large parameter
77- GalambosCopula (2 , 4.3 ),
78- GalambosCopula (2 , 120 ),
79-
80- # Gaussian
81- GaussianCopula ([1 0.7 ; 0.7 1 ]),
82-
83- # Gumbel-Barnett
84- GumbelBarnettCopula (2 , 1.0 ),
85- GumbelBarnettCopula (3 , 0.35 ),
86-
87- # Gumbel: 2D and non-2D
88- GumbelCopula (2 , 1.2 ),
89- GumbelCopula (4 , 7.0 ),
90-
91- # Hüsler–Reiss
92- HuslerReissCopula (2 , 3.5 ),
93-
94- # Independent: prefer non-2D
95- IndependentCopula (4 ),
96-
97- # Inverse Gaussian: 2D and non-2D
98- InvGaussianCopula (2 , 1.0 ),
99- InvGaussianCopula (4 , 0.05 ),
100-
101- # Joe: include ∞ special case and one non-2D
102- JoeCopula (2 , Inf ),
103- JoeCopula (3 , 7 ),
104-
105- # Log copula
106- LogCopula (2 , 1.5 ),
107-
108- # Marshall–Olkin variants
109- MCopula (4 ),
110- MixedCopula (2 , 0.5 ),
111- MOCopula (2 , 0.5 , 0.5 , 0.5 ),
112-
113- # Plackett
114- PlackettCopula (2.0 ),
115-
116- # Raftery: prefer non-2D
117- RafteryCopula (3 , 0.5 ),
118-
119- # t-Copula: prefer non-2D
120- TCopula (4 , [1 0.5 ; 0.5 1 ]),
121-
122- # t-EV: one representative
123- tEVCopula (2 , 4.0 , 0.5 ),
124-
125- # W copula
126- WCopula (2 ),
127- ]);
128-
129- let rng = StableRNG (123 )
130- top = SUITE
131- # helper to get stable display names
132- _show_name (C) = sprint (show, C)
133- # helper to ensure nested groups exist and return them
134- function ensure_group! (grp:: BenchmarkGroup , key)
135- if haskey (grp, key)
136- return grp[key]
137- else
138- sub = BenchmarkGroup ()
139- grp[key] = sub
140- return sub
141- end
8+ function exercise (rng, C)
9+ d = length (C)
10+ u = rand (rng, C, 5 )
11+ c = cdf (C, u)
12+ p = pdf (C, u)
13+ r = rosenblatt (C, u)
14+ ir = inverse_rosenblatt (C, r)
15+ return nothing
16+ end
17+ function metrics (C)
18+ Copulas. τ (C)
19+ Copulas. ρ (C)
20+ Copulas. β (C)
21+ Copulas. γ (C)
22+ Copulas. ι (C)
23+ return nothing
24+ end
25+ function fitting (rng, C)
26+ d = length (C)
27+ CT = typeof (C)
28+ u = rand (rng, C, 10 )
29+ for m in Copulas. _available_fitting_methods (CT, d)
30+ fit (CT, u, m)
31+ fit (CopulaModel, CT, u, m)
14232 end
33+ return nothing
34+ end
35+ function conditioning (rng, C)
36+ d = length (C)
37+ u = rand (rng, C)
38+ D = condition (C, 2 : d, u[2 : d,1 ])
39+ cdf (D, rand (rng))
40+ quantile (D, rand (rng))
41+ return nothing
42+ end
14343
144- for C in EXAMPLES # only the first two for the moment to see.
145- CT, d = typeof (C), length (C)
146- name_full = _show_name (C)
147-
148- # Pre-generate inputs for cdf/pdf/rosenblatt and inverse
149- u = rand (rng, C, 5 )
150- v = rand (rng, d, 5 ) # uniform
151-
152- # Core ops grouped first by op, then by copula name
153- ensure_group! (top, " rng" )[name_full] = @benchmarkable rand ($ rng, $ C, 64 )
154- ensure_group! (top, " cdf" )[name_full] = @benchmarkable cdf ($ C, $ u)
155- # ensure_group!(top, "pdf")[name_full] = @benchmarkable pdf($C, $u)
156- # ensure_group!(top, "rbt")[name_full] = @benchmarkable rosenblatt($C, $u)
157- # ensure_group!(top, "irbt")[name_full] = @benchmarkable inverse_rosenblatt($C, $v)
158-
159- # # Metrics: scalar and matrix-style
160- # mgrp = ensure_group!(top, "metrics")
161- # ensure_group!(mgrp, "τ")[name_full] = @benchmarkable Copulas.τ($C)
162- # ensure_group!(mgrp, "ρ")[name_full] = @benchmarkable Copulas.ρ($C)
163- # ensure_group!(mgrp, "β")[name_full] = @benchmarkable Copulas.β($C)
164- # ensure_group!(mgrp, "γ")[name_full] = @benchmarkable Copulas.γ($C)
165- # ensure_group!(mgrp, "ι")[name_full] = @benchmarkable Copulas.ι($C)
166- # ensure_group!(mgrp, "corτ")[name_full] = @benchmarkable StatsBase.corkendall($C)
167- # ensure_group!(mgrp, "corρ")[name_full] = @benchmarkable StatsBase.corspearman($C)
168- # ensure_group!(mgrp, "corβ")[name_full] = @benchmarkable Copulas.corblomqvist($C)
169- # ensure_group!(mgrp, "corγ")[name_full] = @benchmarkable Copulas.corgini($C)
170- # ensure_group!(mgrp, "corι")[name_full] = @benchmarkable Copulas.corentropy($C)
171-
172- # # Fitting: iterate available methods for this copula type
173- # fitgrp = ensure_group!(top, "fit")
174- # for m in Copulas._available_fitting_methods(CT, d)
175- # ensure_group!(fitgrp, string(m))[name_full] = @benchmarkable fit($CT, $u, $m)
176- # end
177-
178- # # Conditioning: distortions (any d>=2) and bivariate conditional copulas (if d>3)
179- # condgrp = ensure_group!(top, "cond")
180- # D1 = condition(C, 2:d, u[2:d,1]) # condition the copula on the first sampled point.
181- # t = rand(rng, 32)
182- # ensure_group!(condgrp, "dst/cdf")[name_full] = @benchmarkable Distributions.cdf($D1, $t)
183- # ensure_group!(condgrp, "dst/quantile")[name_full] = @benchmarkable Distributions.quantile($D1, $t)
44+ function run_benches ()
45+ rng = StableRNG (123 )
46+
47+ EXAMPLES = unique ([
48+ AMHCopula (3 , 0.2 ),
49+ ArchimaxCopula (2 , Copulas. BB1Generator (1.3 , 1.4 ), Copulas. GalambosTail (0.7 )),
50+ ArchimaxCopula (2 , Copulas. ClaytonGenerator (1.5 ), Copulas. HuslerReissTail (0.6 )),
51+ ArchimaxCopula (2 , Copulas. FrankGenerator (6.0 ), Copulas. LogTail (1.5 )),
52+ ArchimaxCopula (2 , Copulas. GumbelGenerator (2.0 ), Copulas. AsymGalambosTail (0.35 , 0.65 , 0.3 )),
53+ ArchimaxCopula (2 , Copulas. JoeGenerator (2.5 ), Copulas. GalambosTail (2.5 )),
54+ ArchimedeanCopula (3 , EmpiricalGenerator (randn (rng, 3 , 200 ))),
55+ AsymGalambosCopula (2 , 5.0 , 0.8 , 0.3 ),
56+ AsymLogCopula (2 , 1.5 , 0.5 , 0.2 ),
57+ AsymMixedCopula (2 , 0.12 , 0.13 ),
58+ BB10Copula (2 , 3.0 , 0.8 ),
59+ BB1Copula (2 , 1.2 , 1.5 ),
60+ BB2Copula (2 , 1.5 , 1.8 ),
61+ BB3Copula (2 , 2.5 , 0.5 ),
62+ BB6Copula (2 , 1.5 , 1.4 ),
63+ BB7Copula (2 , 1.5 , 0.4 ),
64+ BB8Copula (2 , 1.5 , 0.6 ),
65+ BB9Copula (2 , 2.0 , 1.5 ),
66+ BC2Copula (2 , 0.5 , 0.5 ),
67+ BC2Copula (2 , 0.7 , 0.3 ),
68+ BernsteinCopula (ClaytonCopula (3 , 3.3 ); m= 5 ),
69+ BernsteinCopula (randn (rng, 3 ,100 ); m= 5 , pseudo_values= false ),
70+ BetaCopula (randn (rng, 3 ,100 )),
71+ CheckerboardCopula (randn (rng, 3 ,100 ); pseudo_values= false ),
72+ ClaytonCopula (2 , - 0.7 ),
73+ ClaytonCopula (4 , 3.0 ),
74+ Copulas. SubsetCopula (RafteryCopula (3 , 0.5 ), (2 ,1 )),
75+ CuadrasAugeCopula (2 , 0.0 ),
76+ CuadrasAugeCopula (2 , 0.8 ),
77+ EmpiricalCopula (randn (2 ,20 ), pseudo_values= false ),
78+ EmpiricalEVCopula (randn (rng, 2 ,20 ); method= :pickands , pseudo_values= false ),
79+ FGMCopula (2 , 1 ),
80+ FGMCopula (3 , [0.1 ,0.2 ,0.3 ,0.4 ]),
81+ FrankCopula (2 , - 5 ),
82+ FrankCopula (4 , 5 ),
83+ GalambosCopula (2 , 4.3 ),
84+ GalambosCopula (2 , 120 ),
85+ GaussianCopula ([1 0.7 ; 0.7 1 ]),
86+ GumbelBarnettCopula (2 , 1.0 ),
87+ GumbelBarnettCopula (3 , 0.35 ),
88+ GumbelCopula (2 , 1.2 ),
89+ GumbelCopula (4 , 7.0 ),
90+ HuslerReissCopula (2 , 3.5 ),
91+ IndependentCopula (4 ),
92+ InvGaussianCopula (2 , 1.0 ),
93+ InvGaussianCopula (4 , 0.05 ),
94+ JoeCopula (2 , Inf ),
95+ JoeCopula (3 , 7 ),
96+ LogCopula (2 , 1.5 ),
97+ MCopula (4 ),
98+ MixedCopula (2 , 0.5 ),
99+ MOCopula (2 , 0.5 , 0.5 , 0.5 ),
100+ PlackettCopula (2.0 ),
101+ RafteryCopula (3 , 0.5 ),
102+ TCopula (4 , [1 0.5 ; 0.5 1 ]),
103+ tEVCopula (2 , 4.0 , 0.5 ),
104+ WCopula (2 ),
105+ ]);
106+
107+ G = BenchmarkGroup ()
184108
185- # if d > 3
186- # CC = condition(C, 3:d, u[3:d,1])
187- # Ucc = rand(rng, CC, 64)
188- # Vcc = rand(rng, 2, 64)
189- # ensure_group!(condgrp, "cc/rng")[name_full] = @benchmarkable rand($rng, $CC, 64)
190- # ensure_group!(condgrp, "cc/cdf")[name_full] = @benchmarkable cdf($CC, $Ucc)
191- # ensure_group!(condgrp, "cc/pdf")[name_full] = @benchmarkable pdf($CC, $Ucc)
192- # ensure_group!(condgrp, "cc/rbt")[name_full] = @benchmarkable rosenblatt($CC, $Ucc)
193- # ensure_group!(condgrp, "cc/irbt")[name_full] = @benchmarkable inverse_rosenblatt($CC, $Vcc)
194- # end
109+ for C in EXAMPLES # only the first two for the moment to see.
110+ tp = typeof (C). name. wrapper
111+ nm = sprint (show, C)
112+ @show nm
113+ G[" exercise" ][tp][nm] = @be exercise (rng, C)
114+ # G["metrics"][nm] = @be metrics(C)
115+ # G["fitting"][nm] = @be fitting(rng, C)
116+ # G["conditioning"][tp][nm] = @be conditioning(rng, C)
195117 end
118+ return (G)
196119end
197120
198-
199- # Separate SklarDist benchmarks on a single representative model (Clayton d=5)
200- # let rng = StableRNG(321)
201- # top = SUITE["sklar"] = BenchmarkGroup()
202- # C = ClaytonCopula(5, 2.0)
203- # m = (Distributions.Normal(), Distributions.LogNormal(), Distributions.Gamma(2,2), Distributions.Beta(2,5), Distributions.Uniform())
204- # S = SklarDist(C, m)
205- # X = rand(rng, S, 128)
206- # U = pseudos(X)
207- # top["rand/128"] = @benchmarkable rand($rng, $S, 128)
208- # top["cdf/128"] = @benchmarkable cdf($S, $X)
209- # top["pdf/128"] = @benchmarkable pdf($S, $X)
210- # top["rosenblatt/128"] = @benchmarkable rosenblatt($S, $X)
211- # V = rand(rng, 5, 128)
212- # top["inverse_rosenblatt/128"] = @benchmarkable inverse_rosenblatt($S, $V)
213- # # Fitting pathways (keep light)
214- # top["fit/ifm"] = @benchmarkable Distributions.fit(CopulaModel, SklarDist{ClaytonCopula, typeof(m)}, $X; sklar_method=:ifm, copula_method=:itau, summaries=false)
215- # top["fit/ecdf"] = @benchmarkable Distributions.fit(CopulaModel, SklarDist{ClaytonCopula, typeof(m)}, $X; sklar_method=:ecdf, copula_method=:itau, summaries=false)
216- # end
121+ # PkgBenchmark entrypoint; must define SUITE
122+ const SUITE = run_benches ();
0 commit comments