Skip to content

Commit 01e5218

Browse files
committed
Improvements and bugfixes
- Improved the runtime of the linear extension subroutine for small signals
1 parent cd25932 commit 01e5218

File tree

4 files changed

+50
-22
lines changed

4 files changed

+50
-22
lines changed

cssd.m

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -263,7 +263,7 @@
263263
end
264264
%%% END PELT PRUNING
265265

266-
%%% BEGIN FPVVI PRUNING
266+
%%% BEGIN FPVI PRUNING
267267
otherwise
268268
for rb=3:N
269269

demos/Ex_Stock_CV.m

Lines changed: 23 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -73,11 +73,28 @@
7373

7474
%% run again with the PELT pruning for runtime comparison
7575
rng(123)
76-
77-
% starting the optimization with these fine-tuned initial values turned out to
78-
% result in a reasonbly good CV score for this data
79-
p_init = 0.4702;
80-
gamma_init = 0.0069;
8176
tic
8277
output_cv = cssd_cv(x, y, [], [], [], [p_init; gamma_init], 'verbose', 1, 'pruning', 'PELT');
83-
runtime_pelt = toc
78+
runtime_pelt = toc
79+
80+
%% plot result
81+
xx = linspace(min(x), max(x),100000);
82+
fig = figure(1);
83+
clf;
84+
set(gcf, 'name', 'Stock', 'Color', 'white', 'units','normalized', 'position', [0,0,0.3,0.3]);
85+
plot([],[])
86+
hold on
87+
output.pcw_fun.plot(xx, '-', 'Linewidth', 2, 'Color', '#77AC30', 'DisplayName', 'CSSD')
88+
plot(x, y, '.k', 'Markersize', 0.5, 'DisplayName', 'Data')
89+
legend('Location', 'NorthWest')
90+
xlim([min(xx), max(xx)])
91+
for i = 1:numel(discont)
92+
plot([discont(i), discont(i)], ylim, '--', 'Color', '#999999', 'DisplayName','')
93+
end
94+
xticks(discont);
95+
xtickangle(60)
96+
dates_ext_str = datestr(dates_ext);
97+
xticklabels(dates_ext_str(round(xticks),:));
98+
hold off
99+
leg = legend;
100+
legend(leg.String{1:3})

demos/ruptures_cssd.py

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,8 @@
55
import time
66
import cProfile
77
import pstats
8+
import math
9+
810

911
class CSSD_baseline(BaseCost):
1012

@@ -64,8 +66,11 @@ def detect_changepoints(x,y, p, gamma, delta):
6466
cost.num_elems = 0
6567

6668
# invoke PELT method
67-
algo = rpt.Pelt(custom_cost=cost, min_size=1, jump=1).fit(y)
68-
result = algo.predict(pen=gamma)
69+
if math.isinf(gamma):
70+
result = []
71+
else:
72+
algo = rpt.Pelt(custom_cost=cost, min_size=1, jump=1).fit(y)
73+
result = algo.predict(pen=gamma)
6974
elapsed_time = time.time() - start_time
7075

7176
return result, elapsed_time, cost.num_calls, cost.num_elems

subroutines/linext_pp.m

Lines changed: 19 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -3,22 +3,28 @@
33
%to the boundaries [l, r]
44

55
assert( (l <= pp.breaks(1)) && (pp.breaks(end) <= r), 'New boundaries must be larger than the old ones for extension.')
6+
pp = embed_pptocubic(pp);
67

7-
% extends the boundaries by one in each direction and continues the spline
8-
% linearly (fnxtr is Matlab built-in)
9-
pp = fnxtr(pp,2);
8+
pp_deriv = pp;
9+
pp_deriv.coefs = pp_deriv.coefs(:, 1:3) .* [3,2,1];
10+
pp_deriv.order = 3;
11+
first = pp.breaks(1);
12+
last = pp.breaks(end);
1013

11-
% adjust the right bound
12-
pp.breaks(end) = r;
14+
new_breaks = [l, pp.breaks, r];
15+
base_last = ppval(pp, last);
1316

14-
% when changing the first break, the base point of the polynomial is changed
15-
% which requires a corrected
16-
for i = 1:pp.dim % loop over all dimensions
17-
a = pp.coefs(i,end-1);
18-
pp.coefs(i,end) = pp.coefs(i,end) - a * (pp.breaks(1) - l);
19-
% finally adjust the endpoints
20-
end
21-
pp.breaks(1) = l;
17+
slope_last = ppval(pp_deriv, last);
18+
19+
base_first = ppval(pp, first);
20+
slope_first = ppval(pp_deriv, first);
21+
base_l = base_first + slope_first .* (l - first);
22+
23+
new_coefs = [zeros(pp.dim, 2), slope_first, base_l; pp.coefs; zeros(pp.dim, 2), slope_last, base_last];
24+
25+
pp.breaks = new_breaks;
26+
pp.coefs = new_coefs;
27+
pp.pieces = pp.pieces + 2;
2228

2329
end
2430

0 commit comments

Comments
 (0)