Mercurial > hg > camir-aes2014
diff toolboxes/MIRtoolbox1.3.2/MIRToolbox/mircluster.m @ 0:e9a9cd732c1e tip
first hg version after svn
author | wolffd |
---|---|
date | Tue, 10 Feb 2015 15:05:51 +0000 |
parents | |
children |
line wrap: on
line diff
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/toolboxes/MIRtoolbox1.3.2/MIRToolbox/mircluster.m Tue Feb 10 15:05:51 2015 +0000 @@ -0,0 +1,238 @@ +function [a d] = mircluster(a,varargin) +% c = mircluster(a,f) clusters the segments in the audio sequence(s) +% contained in the audio object a, along the analytic feature(s) +% f, using the k-means strategy. Multiple analytic features have to +% be grouped into one array of cells. +% Example: +% sg = mirsegment(a); +% mircluster(sg, mirmfcc(sg)) +% mircluster(sg, {mirmfcc(sg), mircentroid(sg)}) +% c = mircluster(d) clusters the frame-decomposed data d into groups +% using K-means clustering. +% Example: +% cc = mirmfcc(a,'Frame'); +% mircluster(cc) +% Optional argument: +% mircluster(...,n) indicates the maximal number of clusters. +% Default value: n = 2. +% mircluster(...,'Runs',r) indicates the maximal number of runs. +% Default value: r = 5. +% +% Requires SOM Toolbox (included in the MIRtoolbox distribution). + + + nruns.key = 'Runs'; + nruns.type = 'Integer'; + nruns.default = 5; + option.nruns = nruns; + + nclust.position = 2; + nclust.type = 'Integer'; + nclust.default = 2; + option.nclust = nclust; + +specif.option = option; + +specif.nochunk = 1; + +d = a; +if isa(a,'mirdesign') + if not(get(a,'Eval')) + % During bottom-up construction of the general design + + [unused option] = miroptions(@mircluster,a,specif,varargin); + type = get(a,'Type'); + a = mirdesign(@mircluster,a,option,{},struct,type); + a = set(a,'NoChunk',1); + else + % During top-down evaluation initiation + + e = evaleach(a); + if iscell(e) + e = e{1}; + end + a = mircluster(e,varargin{:}); + end +else + if not(isa(a,'mirdata')) + mirerror('mircluster','The input should be either frame- or segment-decomposed.'); + end + + if isempty(varargin) || (not(isa(varargin{1},'mirdata') || ... + (iscell(varargin{1}) && ... + isa(varargin{1}{1},'mirdata')))) + % mircluster version for frame-decomposed data: + % frames are clustered into groups using K-means clustering. + [unused option] = miroptions(@mircluster,a,specif,varargin); + da = get(a,'Data'); + lva = length(da); % Number of audio files in the audio object. + c = cell(1,lva); + display('Clustering frames...'); + if mirwaitbar + handle = waitbar(0,'Clustering frames...'); + else + handle = 0; + end + for j = 1:lva % For each audio file,... + va = []; % Data transmitted to the kmeans_cluster function. + v = da{j}; + if iscell(v) + v = uncell(v,-Inf); %v{1}; + end + if size(v,4)>1 + v(end+1:2*end,:,:,1) = v(:,:,:,2); + v(:,:,:,2) = []; + end + % Standardization + %stv = std(v,0,2); + %stv(find(stv == 0)) = 1; + va(end+1:end+size(v,1),:,:) = v;%... + %(v - repmat(mean(v,2),[1 size(v,2) ])) ... + %./ repmat(stv,[1 size(v,2) ]); + if isa(a,'mirscalar') + m = get(a,'Mode'); + if not(isempty(m)) + m = m{j}; + val = []; + for l = 1:nseg + vl = m{l}; + if iscell(vl) + vl = vl{1}; + end + val(:,l) = vl; + end + stv = std(val,0,2); + stv(find(stv == 0)) = 1; + va(end+1:end+size(val,1),:) = ... + (val - repmat(mean(val,2),[1 size(val,2) ])) ... + ./ repmat(stv,[1 size(val,2) ]); + end + end + if size(va,3)>1 + mel = 1; + va = reshape(va,size(va,2),size(va,3))'; + else + mel = 0; + end + [cc, p, err, ind] = kmeans_clusters(va',option.nclust,option.nruns); + [minind select] = min(ind); + c{j}.centr = cc{select}'; + c{j}.index = p{select}; + c{j}.weight = zeros(1,size(cc{select},1)); + c{j}.covar = zeros(size(cc{select}')); + ii = 1; + for i = 1:size(c{j}.centr,2) + clus = va(:,c{j}.index == ii); + if isempty(clus) + higher = find(c{j}.index > ii); + c{j}.index(higher) = c{j}.index(higher)-1; + c{j}.centr(:,ii) = []; + c{j}.weight(ii) = []; + c{j}.covar(:,ii) = []; + else + c{j}.weight(ii) = size(clus,2)/size(va,2); + if c{j}.weight(ii) == 0 + pause + end + c{j}.covar(:,ii) = mean((clus'-ones(1,size(clus,1))*c{j}.centr(:,ii)).^2); + ii = ii+1; + end + end + if handle + waitbar(j/lva,handle); + end + end + if handle + delete(handle) + end + a = set(a,'Clusters',c); + else + % mircluster version for segmented audio: + % segments are clustered into groups using K-means clustering. + da = varargin{1}; + varargin(1) = []; + [unused option] = miroptions(@mircluster,a,specif,varargin); + display('Clustering segments...'); + if isa(da,'mirdata') || (iscell(da) && isa(da{1},'mirdata')) + if not(iscell(da)) + da = {da}; + end + vala = get(a,'Data'); % Data contained in the audio object a. + lva = length(vala); % Number of audio files in the audio object. + clus = cell(1,lva); + for j = 1:lva % For each audio file,... + va = []; % Data transmitted to the kmeans_cluster function. + nseg = length(vala{j}); % Number of segments in the audio file. + for i = 1:length(da) % For each analytic feature,... + v = get(da{i},'Data'); + v = v{j}; + if iscell(v) + v = uncell(v,-Inf); %v{1}; + end + val = []; + if size(v,4)>1 + v(end+1:2*end,:,:,1) = v(:,:,:,2); + v(:,:,:,2) = []; + end + + % Standardization + stv = std(v,0,2); + stv(find(stv == 0)) = 1; + va(end+1:end+size(v,1),:) = ... + (v - repmat(mean(v,2),[1 size(v,2) ])) ... + ./ repmat(stv,[1 size(v,2) ]); + if isa(da{i},'mirscalar') + m = get(da{i},'Mode'); + if not(isempty(m)) + m = m{j}; + val = []; + for l = 1:nseg + vl = m{l}; + if iscell(vl) + vl = vl{1}; + end + val(:,l) = vl; + end + stv = std(val,0,2); + stv(find(stv == 0)) = 1; + va(end+1:end+size(val,1),:) = ... + (val - repmat(mean(val,2),[1 size(val,2) ])) ... + ./ repmat(stv,[1 size(val,2) ]); + end + end + + end + [cc, p, err, ind] = kmeans_clusters(va',min(option.nclust,nseg),option.nruns); + clus{j} = p{end}; + end + a = set(a,'Clusters',clus); + t = get(a,'Time'); + fp = get(a,'FramePos'); + for j = 1:lva % For each audio file,... + aj = vala{j}; + tj = t{j}; + fpj = fp{j}; + clj = clus{j}; + k = 2; + while k <= length(aj) + if clj(k) == clj(k-1) + aj{k-1} = [aj{k-1};aj{k}]; + aj(k) = []; + tj{k-1} = [tj{k-1};tj{k}]; + tj(k) = []; + fpj{k-1} = [fpj{k-1}(1);fpj{k}(2)]; + fpj(k) = []; + clj(k) = []; + k = k-1; + end + k = k+1; + end + vala{j} = aj; + t{j} = tj; + fp{j} = fpj; + cl{j} = clj; + end + a = set(a,'Data',vala,'Time',t,'FramePos',fp,'Clusters',cl); + end + end +end \ No newline at end of file