comparison m-toolbox/classes/@ao/timeaverage.m @ 0:f0afece42f48

Import.
author Daniele Nicolodi <nicolodi@science.unitn.it>
date Wed, 23 Nov 2011 19:22:13 +0100
parents
children
comparison
equal deleted inserted replaced
-1:000000000000 0:f0afece42f48
1 % TIMEAVERAGE Averages time series intervals
2 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
3 %
4 % DESCRIPTION: Averages time series intervals and return a reduced time
5 % series where each point represents the average of a stretch of data.
6 % Despite the name this method can perform some different operations on the
7 % data stretches or apply a user supplied function. Different functions can
8 % be applied to X and Y data.
9 %
10 % CALL: BS = timeaverage(A1, A2, A3, ..., PL)
11 %
12 % INPUTS: AN - time series AOs
13 % PL - parameters list
14 %
15 % OUTPUTS: BS - array of AOs
16 %
17 % <a href="matlab:utils.helper.displayMethodInfo('ao', 'timeaverage')">Parameters Description</a>
18 %
19 % EXAMPLES:
20 %
21 % >> times = [ 0 100 200 300 400 500 ]
22 % >> timeaverage(a, plist('times', times))
23 % >> timeaverage(a, plist('start', 0, 'duration', 100, 'decay', 10, 'repetitions', 3))
24 % >> timeaverage(a, plist('times', times, 'function', 'center'))
25 % >> timeaverage(a, plist('times', times, 'function', @mean))
26 % >> timeaverage(a, plist('times', times, 'xfunction', @min, 'yfunction', @mean))
27 %
28 % NOTES: The intervals are defined as ti <= x < te where ti is the start
29 % time and te is the end time of each interval. If not specified the TIMES
30 % vector is constructed from other parameters using the following schema
31 % repeated accordingly a number of times specified with the REPETITIONS
32 % parameter.
33 %
34 % settling duration decay settling duration
35 % |------------|##############|---------|------------|##############|---
36 % START
37 %
38 %
39 % VERSION: $Id: timeaverage.m,v 1.10 2011/05/16 09:31:35 mauro Exp $
40 %
41 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
42
43 function varargout = timeaverage(varargin)
44
45 % check if this is a call for parameters
46 if utils.helper.isinfocall(varargin{:})
47 varargout{1} = getInfo(varargin{3});
48 return
49 end
50
51 import utils.const.*
52 utils.helper.msg(msg.PROC3, 'running %s/%s', mfilename('class'), mfilename);
53
54 % collect input variable names
55 in_names = cell(size(varargin));
56 for ii = 1:nargin,in_names{ii} = inputname(ii);end
57
58 % collect all AOs and plists
59 [as, ao_invars] = utils.helper.collect_objects(varargin(:), 'ao', in_names);
60 pl = utils.helper.collect_objects(varargin(:), 'plist', in_names);
61
62 % decide on a deep copy or a modify
63 bs = copy(as, nargout);
64
65 % accept spaces dashes or underscores
66 pl = fixpnames(pl);
67
68 % combine plists
69 pl = combine(pl, getDefaultPlist());
70
71 % splitting by time takes the precedence
72 times = find(pl, 'times');
73
74 % otherwise construct a times vector based on other parameters
75 if isempty(times)
76 start = find(pl, 'start', find(pl, 'start time'));
77 repeat = find(pl, 'repetitions');
78 duration = find(pl, 'duration');
79 settling = find(pl, 'settling', find(pl, 'settling time'));
80 decay = find(pl, 'decay', find(pl, 'decay time'));
81
82 times = zeros(repeat*2, 1);
83 for kk = 1:repeat
84 times(2*kk-1) = start + settling*kk + duration*(kk-1) + decay*(kk-1);
85 times(2*kk) = start + settling*kk + duration*kk + decay*(kk-1);
86 end
87 end
88
89 % check that the times vector as the right dimensions
90 if mod(numel(times), 2)
91 error('### times defines times intervals with an even number of points');
92 end
93
94 % select which functions to apply to the data stretches
95 method = lower(find(pl, 'method'));
96 funct = find(pl, 'function');
97 if isempty(funct)
98 funct = method;
99 end
100 xfunct = find(pl, 'xfunction', funct);
101 yfunct = find(pl, 'yfunction', funct);
102 if isempty(xfunct)
103 xfunct = funct;
104 end
105 if isempty(yfunct)
106 yfunct = funct;
107 end
108
109 % loop over input AOs
110 for jj = 1:numel(bs)
111
112 % check input data
113 if ~isa(bs(jj).data, 'tsdata')
114 warning('LTPDA:isNotTsdata', '!!! %s is not a tsdata AO and will be ingnored', bs(jj).name);
115 continue;
116 end
117
118 [xmean, ymean, dy] = split_and_apply(bs(jj).x, bs(jj).y, times, xfunct, yfunct);
119
120 % assign values
121 bs(jj).setXY(xmean, ymean);
122 bs(jj).setDy(dy);
123
124 % set name
125 bs(jj).name = sprintf('%s(%s)', mfilename, ao_invars{jj});
126 % add history
127 bs(jj).addHistory(getInfo('None'), pl, ao_invars(jj), bs(jj).hist);
128
129 end % loop over analysis objects
130
131 % set output
132 if nargout == numel(bs)
133 % list of outputs
134 for ii = 1:numel(bs)
135 varargout{ii} = bs(ii);
136 end
137 else
138 % single output
139 varargout{1} = bs;
140 end
141 end
142
143
144 function ii = getInfo(varargin)
145 if nargin == 1 && strcmpi(varargin{1}, 'None')
146 sets = {};
147 pl = [];
148 else
149 sets = {'Default'};
150 pl = getDefaultPlist;
151 end
152 % build info object
153 ii = minfo(mfilename, 'ao', 'ltpda', utils.const.categories.sigproc, '$Id: timeaverage.m,v 1.10 2011/05/16 09:31:35 mauro Exp $', sets, pl);
154 % set the default property of the method as modifier or not
155 ii.setModifier(true);
156 % set the minumum number of inputs and outputs for the block
157 ii.setArgsmin(1);
158 ii.setOutmin(1);
159 end
160
161
162 function plout = getDefaultPlist()
163 persistent pl;
164 if exist('pl', 'var')==0 || isempty(pl)
165 pl = buildplist();
166 end
167 plout = pl;
168 end
169
170 function pl = buildplist()
171 pl = plist;
172
173 % method
174 p = param({'method','Reduction method to apply to data stretches.'}, ...
175 {1, {'MEAN', 'MEDIAN', 'MAX', 'MIN', 'RMS', 'CENTER'}, paramValue.SINGLE});
176 pl.append(p);
177
178 % function
179 p = param({'function', ['Function to apply to data stretches. It can be' ...
180 ' a function name or a function handle to a function that accepts'...
181 ' a vector and returns a scalar.']}, paramValue.EMPTY_DOUBLE);
182 pl.append(p);
183
184 % x function
185 p = param({'xfunction', ['Function to apply to X data stretches. It can be' ...
186 ' a function name or a function handle to a function that accepts'...
187 ' a vector and returns a scalar.']}, paramValue.EMPTY_DOUBLE);
188 pl.append(p);
189
190 % y function
191 p = param({'yfunction', ['Function to apply to Y data stretches. It can be' ...
192 ' a function name or a function handle to a function that accepts'...
193 ' a vector and returns a scalar.']}, paramValue.EMPTY_DOUBLE);
194 pl.append(p);
195
196 % times
197 p = param({'times', 'An array of start-stop times to split by.'}, paramValue.DOUBLE_VALUE([]));
198 pl.append(p);
199
200 % start time
201 p = param({'start time', 'Start time of the measurement.'}, paramValue.DOUBLE_VALUE(0));
202 pl.append(p);
203
204 % duration
205 p = param({'duration', 'Duration of each cicle.'}, paramValue.DOUBLE_VALUE(0));
206 pl.append(p);
207
208 % repetitions
209 p = param({'repetitions', 'Number of cycles.'}, paramValue.DOUBLE_VALUE(1));
210 pl.append(p);
211
212 % settling time
213 p = param({'settling time', 'Settling time in each cicle.'}, paramValue.DOUBLE_VALUE(0));
214 pl.append(p);
215
216 % decay time
217 p = param({'decay time', 'Decay time in each cicle.'}, paramValue.DOUBLE_VALUE(0));
218 pl.append(p);
219
220 end
221
222
223 function pl = fixpnames(pl)
224 % replace underscores and dashes in parameters names with spaces
225 if isa(pl, 'plist')
226 for ii = 1:pl.nparams
227 pl.params(ii).setKey(strrep(strrep(pl.params(ii).key, '_', ' '), '-', ' '));
228 end
229 end
230 end
231
232
233 function xmean = center(x) %#ok<DEFNU>
234 % computes the center of an interval defined by
235 % the minimum and maximum values in an array
236 xmean = mean([min(x) max(x)]);
237 end
238
239
240 function [xmean, ymean, dy] = split_and_apply(x, y, times, xfunct, yfunct)
241
242 % number of intervals
243 nint = numel(times) / 2;
244
245 xmean = zeros(nint, 1);
246 ymean = zeros(nint, 1);
247
248 % for the mean we are able to compute uncertainty too
249 if ischar(yfunct) && strcmp(yfunct, 'mean')
250 dy = zeros(nint, 1);
251 else
252 dy = [];
253 end
254
255 % loop over the intervals
256 for kk = 1:nint
257
258 % create index of the interval
259 is = times(2*kk-1);
260 ie = times(2*kk);
261 idx = x >= is & x < ie;
262
263 % apply functions to interval
264 xmean(kk) = feval(xfunct, x(idx));
265 ymean(kk) = feval(yfunct, y(idx));
266
267 if ~isempty(dy)
268 % compute uncertainty as the standard deviation of the mean
269 dy(kk) = std(y(idx)) / sqrt(length(x(idx)));
270 end
271
272 end
273 end