3 % method determining interpolation points
for rbf (radial basis
function)
4 % interpolation of a given
function via
cubegrid refinements in
11 % required fields of params:
14 % check
for parameters
15 if ~isfield(params,
'tolerance')
16 params.tolerance = 1e-3;
19 if ~isfield(params, 'nmax')
20 params.nmax = 4*2^length(params.range);
23 if ~isfield(params, 'domain_corners')
24 params.domain_corners = 1;
27 if ~isfield(params, 'midpoint_version')
28 params.midpoint_version = 1;
29 elseif ~params.midpoint_version
30 params.domain_corners = 1;
37 if ~isfield(params, 'kernel_type')
38 params.kernel_type = 'gaussian_loc';
41 if ~isfield(params, 'dilation')
42 params.dilation = 0.3;
45 if ~isfield(params, 'penalize_factor')
46 params.penalize_factor = 0.5;
50 disp('enter
cubegrid interpolation greedy');
57 start_algorithm = tic;
60 params.numintervals = ones(length(params.range), 1);
63 % construct interpolant
function
64 interp_func =
RbfInterpolant(zeros(grid.dimension, 0), [], params.kernel_type, params.dilation);
66 % input
for adaptive algorithm
81 disp(
'start greedy algorithm');
87 % determine
new points
for interpolant
function
88 new_vertices = zeros(0, grid.dimension);
89 if ~params.midpoint_version || (params.domain_corners && grid.refine_steps == 0)
91 % determine
new vertices
92 old_ids = grid.creation_step < grid.creation_step(new_ids(1));
93 new_vertex_indices = ...
94 setdiff(grid.vertexindex(new_ids, :), grid.vertexindex(old_ids, :));
96 % detect midpoint vertex
97 new_vertices = grid.vertex(new_vertex_indices, :);
98 [~, dupl_id, ~] = detect_duplicate_rows([C; new_vertices], 1e-10);
99 new_vertices(dupl_id - size(C, 1), :) = [];
103 C_new = get_midpoints(grid, new_ids);
106 % compute
new midpoint data
107 tmp_values = cell(length(new_ids), 1);
108 for i = 1:length(new_ids)
109 tmp_values{i} = func(C_new(i, :)
');
111 V = [V; cell2mat(tmp_values)];
114 errors = min_max_errors(interp_func, C, V, params);
115 max_error = max(errors);
116 max_err_seq = [max_err_seq, max_error];
117 num_points_seq = [num_points_seq, interp_func.num_points];
118 if strncmp(interp_func.kernel_type, 'gaussian
', 8)
119 dilation_seq = [dilation_seq, interp_func.dilation];
123 continue_loop = max_error >= params.tolerance;
125 if params.verbose > 1
126 disp([num2str(interp_func.num_points), '(
', ...
127 num2str(num_points), ') points, max error =
', ...
128 num2str(max_error)]);
131 % if num_points > 0 && exist('rbhdd_plot_infsup_results
', 'file
') == 2
132 % infsup_constant = RbfInterpolant(interp_func.data_points, ...
133 % interp_func.data_values, ...
134 % interp_func.kernel_type, ...
135 % interp_func.dilation);
136 % rbhdd_plot_infsup_results;
137 % if ~isfield(varargout{1}, 'max_test_errs
')
138 % varargout{1}.max_test_errs = [];
140 % varargout{1}.max_test_errs = [varargout{1}.max_test_errs, act_val];
143 if num_points >= params.nmax
145 ['iteration maximum reached, maximal error:
', num2str(max_error)])
151 % compute new vertex data
152 tmp_values = cell(size(new_vertices, 1), 1);
153 for i = 1:size(new_vertices, 1)
154 tmp_values{i} = func(new_vertices(i, :)');
157 % add
new vertex data
158 interp_func.add_data(new_vertices
', cell2mat(tmp_values), ...
159 (interp_func.dilation(end)+(interp_func.num_points>0)*10*eps) * ...
160 ones(size(new_vertices, 1)-(interp_func.num_points==0), 1));
161 all_points = [all_points; new_vertices];
162 all_values = [all_values; cell2mat(tmp_values)];
163 num_points = num_points + size(new_vertices, 1);
165 % again compute errors
166 errors = min_max_errors(interp_func, C, V, params);
167 max_error = max(errors);
168 max_err_seq = [max_err_seq, max_error];
169 num_points_seq = [num_points_seq, interp_func.num_points];
170 if strncmp(interp_func.kernel_type, 'gaussian
', 8)
171 dilation_seq = [dilation_seq, interp_func.dilation];
175 continue_loop = max_error >= params.tolerance;
177 if params.verbose > 1
178 disp([num2str(interp_func.num_points), '(
', ...
179 num2str(num_points), ') points, max error =
', ...
180 num2str(max_error)]);
183 % if num_points > 0 && exist('rbhdd_plot_infsup_results
', 'file
') == 2
184 % infsup_constant = RbfInterpolant(interp_func.data_points, ...
185 % interp_func.data_values, ...
186 % interp_func.kernel_type, ...
187 % interp_func.dilation);
188 % rbhdd_plot_infsup_results;
189 % if ~isfield(varargout{1}, 'max_test_errs
')
190 % varargout{1}.max_test_errs = [];
192 % varargout{1}.max_test_errs = [varargout{1}.max_test_errs, act_val];
195 if num_points >= params.nmax
197 ['iteration maximum reached, maximal error:
', num2str(max_error)])
204 all_points = [all_points; C_new];
205 all_values = [all_values; V(end+1-(length(new_ids):-1:1))];
206 num_points = num_points + length(new_ids);
208 % penalize un-refined for long time
209 widths = sqrt(get_volume(grid, find(grid.isleaf)));
210 inf_ind = errors == inf;
211 indicators = params.penalize_factor*max(widths)^2/min(widths)...
212 *penalize_count/max([penalize_count; 1]) + errors/max_error;
213 indicators(inf_ind) = inf;
215 % determine new refinement id
216 [~, max_id] = max(indicators);
217 refine_id = grid.gid2lid(max_id);
220 nelements_old = grid.nelements;
221 refine(grid, refine_id);
222 new_ids = nelements_old+1:grid.nelements;
225 interp_func.add_data(C(max_id, :)', V(max_id), interp_func.dilation(end)+10*eps);
226 C_added = [C_added; max_id];
227 penalize = setdiff(1:size(C, 1), C_added);
228 penalize_count(max_id) = 0;
229 penalize_count(penalize) = penalize_count(penalize) + 1;
230 penalize_count = [penalize_count; zeros(length(new_ids), 1)];
237 varargout{1}.max_err_seq = max_err_seq;
238 varargout{1}.all_points = all_points;
239 varargout{1}.all_values = all_values;
240 varargout{1}.num_points_seq = num_points_seq;
241 if strncmp(interp_func.kernel_type,
'gaussian', 8)
242 varargout{1}.dilation_seq = dilation_seq;
244 varargout{1}.comp_time = toc(start_algorithm);
247 if params.verbose > 1
248 disp([
'terminate cubegrid interpolation greedy after ', num2str(toc(start_algorithm)), ...
249 ' seconds with ', num2str(interp_func.num_points),
' points.']);
254 function C = get_midpoints(cube_grid, ids)
255 % computes midpoints of elements
258 ids = 1:cube_grid.nelements;
263 C = zeros(n, cube_grid.dimension);
265 for i = 1:cube_grid.dimension
267 X = reshape(cube_grid.vertex(cube_grid.vertexindex(ids, :), i), ...
268 n, size(cube_grid.vertexindex, 2));
269 C(:, i) = 0.5^cube_grid.dimension * sum(X, 2);
274 function errors = min_max_errors(interp_func, points, data, params)
275 %
if gaussian kernel:
276 % determines good dilation parameter(s) via heuristic procedure
277 % always: gives back absolute interpolation errors
279 errors = test_errors(interp_func, points, data);
281 if strncmp(interp_func.kernel_type, 'gaussian', 8)
285 while max(errors) < old_max_error
287 old_max_error = max(errors);
288 dilation = mean(interp_func.dilation) * ...
289 ones(size(interp_func.dilation));
291 interp_func.dilation = 0.5*dilation;
292 errors = test_errors(interp_func, points, data);
294 if max(errors) > old_max_error
296 interp_func.dilation = 2*dilation;
297 errors = test_errors(interp_func, points, data);
299 if max(errors) > old_max_error
301 factors = 0.75:0.125:1.5;
302 nf = length(factors);
303 errors = zeros(size(points, 1), nf);
306 interp_func.dilation = factors(i)*dilation;
307 errors(:, i) = test_errors(interp_func, points, data);
310 [~, index] = min(max(errors, [], 1));
312 interp_func.dilation = factors(index)*dilation;
313 errors = errors(:, index);
322 if strcmp(interp_func.kernel_type, 'gaussian_loc')
324 dilation = interp_func.dilation;
326 for cur_ind = [1:interp_func.num_points, 1:interp_func.num_points]
328 old_max_error = max(errors);
330 dilation(cur_ind) = 0.5*dilation(cur_ind);
331 interp_func.dilation = dilation;
332 errors = test_errors(interp_func, points, data);
334 if max(errors) > old_max_error
336 dilation(cur_ind) = 4*dilation(cur_ind);
337 interp_func.dilation = dilation;
338 errors = test_errors(interp_func, points, data);
340 if max(errors) > old_max_error
342 dilation(cur_ind) = 0.5*dilation(cur_ind);
343 interp_func.dilation = dilation;
344 errors = test_errors(interp_func, points, data);
353 function errors = test_errors(interp_func, points, data)
354 % computes absolute interpolation errors
356 errors = inf*ones(size(points, 1), 1);
358 if interp_func.num_points > 0
360 for i = 1:length(errors)
361 errors(i) = abs(interp_func(points(i, :)') - data(i)) ...
function r = verbose(level, message, messageId)
This function displays messages depending on a message-id and/or a level. Aditionally you can set/res...
A hierarchical cubegrid of arbitrary dimension.
function [ interp_func , varargout ] = cubegrid_interp_greedy(func, params)
method determining interpolation points for rbf (radial basis function) interpolation of a given func...
implements rbf interpolation by thin plate splines or gaussian