Mercurial > hg > ltpda
comparison m-toolbox/classes/@ao/consolidate.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 % CONSOLIDATE resamples all input AOs onto the same time grid. | |
2 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% | |
3 % | |
4 % CONSOLIDATE resamples all input AOs onto the same time grid and truncates all | |
5 % time-series to start at the maximum start time of the inputs and end | |
6 % at the minimum stop time of the inputs. | |
7 % | |
8 % ALGORITHM: | |
9 % 1) Drop duplicate samples (ao/dropduplicates) | |
10 % 2) Interpolate missing samples (ao/interpmissing) | |
11 % 3) Fix uneven sample rate using interpolate (ao/fixfs) | |
12 % 4) Resample to same fs, either max or specified (ao/resample | |
13 % or ao/interp depending on ratio of old and new sample | |
14 % rate) | |
15 % 5) Truncate all vectors to minimum overlap of time-series | |
16 % (ao/split) | |
17 % 6) Resample on to the same timing grid (ao/interp) | |
18 % 7) Truncate all vectors to same number of samples to correct for | |
19 % any rounding errors in previous steps (ao/select) | |
20 % | |
21 % CALL: >> bs = consolidate(as) | |
22 % | |
23 % INPUTS: as - array of at least two time-series analysis objects | |
24 % pl - parameter list (see below) | |
25 % | |
26 % OUTPUTS: bs - array of analysis objects, one for each input | |
27 % | |
28 % <a href="matlab:utils.helper.displayMethodInfo('ao', 'consolidate')">Parameters Description</a> | |
29 % | |
30 % VERSION: $Id: consolidate.m,v 1.32 2011/04/08 08:56:13 hewitson Exp $ | |
31 % | |
32 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% | |
33 | |
34 % 't' - specify a new time vector to resample on to. This | |
35 % will be truncated to fit within the maximum start | |
36 % time and minimum stop time of the inputs. | |
37 % or | |
38 | |
39 function varargout = consolidate(varargin) | |
40 | |
41 % Check if this is a call for parameters | |
42 if utils.helper.isinfocall(varargin{:}) | |
43 varargout{1} = getInfo(varargin{3}); | |
44 return | |
45 end | |
46 | |
47 import utils.const.* | |
48 utils.helper.msg(msg.PROC3, 'running %s/%s', mfilename('class'), mfilename); | |
49 | |
50 % Collect input variable names | |
51 in_names = cell(size(varargin)); | |
52 for ii = 1:nargin,in_names{ii} = inputname(ii);end | |
53 | |
54 % Collect all AOs and plists | |
55 [as, ao_invars] = utils.helper.collect_objects(varargin(:), 'ao', in_names); | |
56 [pl, pl_invars] = utils.helper.collect_objects(varargin(:), 'plist', in_names); | |
57 | |
58 if numel(as) < 2 | |
59 error('### Consolidate requires at least two time-series AOs to work.'); | |
60 end | |
61 | |
62 if nargout == 0 | |
63 error('### Consolidate cannot be used as a modifier. Please give an output variable.'); | |
64 end | |
65 | |
66 % Decide on a deep copy or a modify | |
67 bs = copy(as, nargout); | |
68 na = numel(bs); | |
69 | |
70 % Combine plists | |
71 pl = parse(pl, getDefaultPlist); | |
72 | |
73 % Get only tsdata AOs | |
74 inhists = []; | |
75 for j=1:na | |
76 if ~isa(bs(j).data, 'tsdata') | |
77 bs(j) = []; | |
78 warning('!!! Skipping AO %s - it''s not a time-series AO.', bs(j).name); | |
79 else | |
80 % gather the input history objects | |
81 inhists = [inhists bs(j).hist]; | |
82 end | |
83 end | |
84 | |
85 % If fs is specified, use it. Otherwise, use max of all | |
86 % input AOs. | |
87 fs = find(pl, 'fs'); | |
88 if isempty(fs) | |
89 % compute max fs | |
90 fs = 0; | |
91 for j=1:na | |
92 if bs(j).data.fs > fs | |
93 fs = bs(j).data.fs; | |
94 end | |
95 end | |
96 end | |
97 utils.helper.msg(msg.PROC2, 'resampling all time-series to an fs of %f', fs); | |
98 | |
99 %----------------- Drop all repeated samples | |
100 utils.helper.msg(msg.PROC1, 'drop duplicates'); | |
101 for j=1:na | |
102 utils.helper.msg(msg.PROC2, 'processing %s', bs(j).name); | |
103 dropduplicates(bs(j),pl); | |
104 end | |
105 | |
106 %----------------- Interpolate all missing samples | |
107 utils.helper.msg(msg.PROC1, 'interpolate missing samples'); | |
108 for j=1:na | |
109 utils.helper.msg(msg.PROC2, 'processing %s', bs(j).name); | |
110 interpmissing(bs(j),pl.pset('method', find(pl, 'interp_method'))); | |
111 end | |
112 | |
113 | |
114 %----------------- Fix uneven sampling | |
115 utils.helper.msg(msg.PROC1, 'fixing uneven sample rates'); | |
116 for j=1:na | |
117 utils.helper.msg(msg.PROC2, 'processing %s', bs(j).name); | |
118 fixfs(bs(j),pl.pset('method', find(pl, 'fixfs_method'))); | |
119 end | |
120 %----------------- Resample all vectors to same fs | |
121 utils.helper.msg(msg.PROC1, 'resample to same fs'); | |
122 | |
123 for j=1:na | |
124 % Check the resampling factor | |
125 [P,Q] = utils.math.intfact(fs,bs(j).data.fs); | |
126 if P > 100 || Q > 100 | |
127 utils.helper.msg(msg.PROC2, 'resampling factor too high [%g/%g]. Trying interpolation', P, Q); | |
128 N = length(bs(j).data.getX); | |
129 t = linspace(0, (P*N/Q-1)/fs, P*N/Q); | |
130 interp(bs(j), plist('vertices', t)); | |
131 else | |
132 resample(bs(j), plist('fsout', fs)); | |
133 end | |
134 end | |
135 | |
136 %---------------- Time properties of AOs | |
137 % Find max start time | |
138 start = 0; | |
139 for j=1:na | |
140 dstart = bs(j).data.t0.utc_epoch_milli/1000 + bs(j).data.getX(1); | |
141 if dstart > start | |
142 start = dstart; | |
143 end | |
144 end | |
145 | |
146 % Find min stop time | |
147 stop = 1e20; | |
148 for j=1:na | |
149 dstop = floor(bs(j).data.t0.utc_epoch_milli/1000 + bs(j).data.getX(end)); | |
150 if dstop < stop | |
151 stop = dstop; | |
152 end | |
153 end | |
154 | |
155 %----------------- Truncate all vectors | |
156 utils.helper.msg(msg.PROC1, 'truncate all vectors'); | |
157 utils.helper.msg(msg.PROC2, 'truncating vectors on interval [%.4f,%.4f]', start, stop); | |
158 | |
159 % split each ao | |
160 bs = split(bs, plist('timespan', timespan(start, stop))); | |
161 | |
162 %----------------- Resample all vectors on to the same grid | |
163 utils.helper.msg(msg.PROC1, 'resample to same grid'); | |
164 % compute new time grid | |
165 | |
166 % get the grid from the first AO | |
167 for j=1:na | |
168 toff = start - bs(j).t0.utc_epoch_milli/1000; | |
169 N = length(bs(j).data.getX); | |
170 t = linspace(toff, toff+(N-1)/fs, N); | |
171 interp(bs(j), plist('vertices', t)); | |
172 end | |
173 | |
174 % Now ensure that we have the same data length | |
175 ns = realmax; | |
176 for jj=1:na | |
177 if len(bs(jj)) < ns | |
178 ns = len(bs(jj)); | |
179 end | |
180 end | |
181 | |
182 bs = select(bs, 1:ns); | |
183 | |
184 nsecs = []; | |
185 for j=1:na | |
186 if isempty(nsecs) | |
187 nsecs = bs(j).data.nsecs; | |
188 end | |
189 if nsecs ~= bs(j).data.nsecs | |
190 error('### Something went wrong with the truncation. Vectors don''t span the same time period.'); | |
191 end | |
192 end | |
193 | |
194 %----------------- Set history on output AOs | |
195 | |
196 for j=1:na | |
197 bs(j).name = sprintf('%s(%s)', mfilename, ao_invars{j}); | |
198 bs(j).addHistory(getInfo('None'), pl, ao_invars(j), inhists(j)); | |
199 end | |
200 | |
201 % Set output | |
202 if nargout == numel(bs) | |
203 % List of outputs | |
204 for ii = 1:numel(bs) | |
205 varargout{ii} = bs(ii); | |
206 end | |
207 else | |
208 % Single output | |
209 varargout{1} = bs; | |
210 end | |
211 end | |
212 | |
213 %-------------------------------------------------------------------------- | |
214 % Get Info Object | |
215 %-------------------------------------------------------------------------- | |
216 function ii = getInfo(varargin) | |
217 if nargin == 1 && strcmpi(varargin{1}, 'None') | |
218 sets = {}; | |
219 pl = []; | |
220 else | |
221 sets = {'Default'}; | |
222 pl = getDefaultPlist; | |
223 end | |
224 % Build info object | |
225 ii = minfo(mfilename, 'ao', 'ltpda', utils.const.categories.sigproc, '$Id: consolidate.m,v 1.32 2011/04/08 08:56:13 hewitson Exp $', sets, pl); | |
226 ii.setModifier(false); | |
227 ii.setArgsmin(2); | |
228 end | |
229 | |
230 %-------------------------------------------------------------------------- | |
231 % Get Default Plist | |
232 %-------------------------------------------------------------------------- | |
233 | |
234 function plout = getDefaultPlist() | |
235 persistent pl; | |
236 if exist('pl', 'var')==0 || isempty(pl) | |
237 pl = buildplist(); | |
238 end | |
239 plout = pl; | |
240 end | |
241 | |
242 function pl_default = buildplist() | |
243 pl_default = combine(... | |
244 plist({'fs','The target sampling frequency for consolidate'}, paramValue.EMPTY_DOUBLE),... | |
245 plist({'interp_method', 'The method for the interpolation step'}, {2, {'nearest', 'linear', 'spline', 'cubic'}, paramValue.SINGLE}), ... | |
246 plist({'fixfs_method', 'The method for the fixfs step'}, {1, {'Time', 'Samples'}, paramValue.SINGLE}), ... | |
247 ao.getInfo('dropduplicates').plists,... | |
248 ao.getInfo('interpmissing').plists,... | |
249 ao.getInfo('fixfs').plists); | |
250 end | |
251 |