MATLAB:列联表

MATLAB:列联表,matlab,Matlab,我有一个以下类型的单元格数组: datABC = [45] [67] 'A' [34] [44] 'A' [11] [84] 'A' [23] [68] 'A' [34] [44] 'B' [30] [94] 'B' [304] [414] 'C' [78] [110] 'C'

我有一个以下类型的单元格数组:

 datABC =
           [45]  [67]  'A'
           [34]  [44]  'A'
           [11]  [84]  'A'
           [23]  [68]  'A'
           [34]  [44]  'B'
           [30]  [94]  'B'
           [304]  [414]  'C'
           [78]  [110]  'C'
           [34]  [120]  'C'
现在我必须根据
A
B
&
C
计算第一列和第二列的观察数和平均值

提前感谢。

请放心

让自己适应


既然闸门打开了,我倒不如把我的两分钱投进去

带有循环的解决方案工作得很好,但您也可以消除循环,以牺牲可读性为代价。首先,您可以使用
unique
获取最后一列中的唯一值:

stringKeys = unique(datABC(:,3))'
然后,可以使用和来计算每个关键点的出现次数:

memberFun = @(x) ismember(datABC(:,3),x);
keyOccurrences = cellfun(@(x) nnz(memberFun(x)),stringKeys)
要计算前两列中每个列对应数据的平均值,可以再次使用非均匀输出的
cellfun

colMeanFun = @(x) mean(reshape([datABC{memberFun(x),1:2}],[],2),1);
colMeans = cellfun(colMeanFun,stringKeys,'UniformOutput',false);
colMeans = vertcat(colMeans{:})
还可以查看ate,它可以用来代替
ismember
,但将忽略大小写

测试数据

datABC = {[45]  [67]  'A'; [34]  [44]  'A'; [11]  [84]  'A'; ...
          [23]  [68]  'A'; [34]  [44]  'B'; [30]  [94]  'B'; ...
          [304] [414] 'C'; [78]  [110] 'C'; [34]  [120] 'C'}; % 9-by-3

既然闸门打开了,我倒不如把我的两分钱投进去

带有循环的解决方案工作得很好,但您也可以消除循环,以牺牲可读性为代价。首先,您可以使用
unique
获取最后一列中的唯一值:

stringKeys = unique(datABC(:,3))'
然后,可以使用和来计算每个关键点的出现次数:

memberFun = @(x) ismember(datABC(:,3),x);
keyOccurrences = cellfun(@(x) nnz(memberFun(x)),stringKeys)
要计算前两列中每个列对应数据的平均值,可以再次使用非均匀输出的
cellfun

colMeanFun = @(x) mean(reshape([datABC{memberFun(x),1:2}],[],2),1);
colMeans = cellfun(colMeanFun,stringKeys,'UniformOutput',false);
colMeans = vertcat(colMeans{:})
还可以查看ate,它可以用来代替
ismember
,但将忽略大小写

测试数据

datABC = {[45]  [67]  'A'; [34]  [44]  'A'; [11]  [84]  'A'; ...
          [23]  [68]  'A'; [34]  [44]  'B'; [30]  [94]  'B'; ...
          [304] [414] 'C'; [78]  [110] 'C'; [34]  [120] 'C'}; % 9-by-3

看起来像是accumarray的工作:

[categories ii jj] = unique(dataABC(:,3));
num = histc(jj,1:max(jj));
mean1 = accumarray(jj, cell2mat(dataABC(:,1)), [], @mean);
mean2 = accumarray(jj, cell2mat(dataABC(:,2)), [], @mean);
例如:

>> dataABC{4,2}

dataABC = 

    [1]    [10]    'A' 
    [2]    [-5]    'B' 
    [3]    [15]    'A' 
    [4]    [40]    'CC'
给予


看起来像是accumarray的工作:

[categories ii jj] = unique(dataABC(:,3));
num = histc(jj,1:max(jj));
mean1 = accumarray(jj, cell2mat(dataABC(:,1)), [], @mean);
mean2 = accumarray(jj, cell2mat(dataABC(:,2)), [], @mean);
例如:

>> dataABC{4,2}

dataABC = 

    [1]    [10]    'A' 
    [2]    [-5]    'B' 
    [3]    [15]    'A' 
    [4]    [40]    'CC'
给予


我必须克制自己。。。做不邮递回答。一个提示。。。cellfun是实现这一点的一种方法,它可能会对您有所帮助:@tmpearce我想到了命令
crosstab
hist
。但不知何故,我无法控制自己。。。做不邮递回答。一个提示。。。cellfun是实现这一点的一种方法,它可能会对您有所帮助:@tmpearce我想到了命令
crosstab
hist
。但不知怎的,我不能。@chappjc我不能像你那样克制自己@嘿,最后你也没有!我只是部分克制——我键入我的答案,删除它,然后等待其他人回答D我觉得这个问题对其他人很有用,所以为什么不等一会儿再回答呢。说真的,
unique
accumarray
配合得很好。当您意识到
unique
的第三个输出本质上为每个唯一值提供了一个整数键时,
accumarray
的使用自然会随之而来+1@chappjc
accumarray
瘾君子@我无法像你那样克制自己@嘿,最后你也没有!我只是部分克制——我键入我的答案,删除它,然后等待其他人回答D我觉得这个问题对其他人很有用,所以为什么不等一会儿再回答呢。说真的,
unique
accumarray
配合得很好。当您意识到
unique
的第三个输出本质上为每个唯一值提供了一个整数键时,
accumarray
的使用自然会随之而来+1@chappjc
accumarray
瘾君子!!