例如,问题的简化版本:
A =
0 10 50
20 30 20
10 70 20
40 20 10
我想获得每列的逻辑标签,其中值在第一四分位数(L),第二和第三四分位数(M)中排名),和第四四分位数(N)。所以最终我可以得到这样的输出:
L =
1 1 0
0 0 0
0 0 0
0 0 1
M =
0 0 0
1 1 1
1 0 1
0 1 0
N =
0 0 1
0 0 0
0 1 0
1 0 0
在这个4x3矩阵示例中,每列有4个值。第一个四分位数(等级)意味着价值最低的那个,第二个和第三个四分位数将取第二个和第三个最低值,第四个四分位数将是具有最高价值的四分位数。所以,在另一个例子中,如果一列有40个值,那么我想标记' 1'对于矩阵中第一个四分位数的最低10个值,依此类推。
想象一下,我有1000x1000矩阵....'分位数'和'百分位'函数不能这样做,因为它们不对每个单元格值进行排名。那么,我应该做些什么呢?
答案 0 :(得分:3)
这是你在找什么?:
pL = prctile(A,25,1);
pU = prctile(A,75,1);
L = bsxfun(@le, A, pL);
N = bsxfun(@ge, A, pU);
M = ones(size(A))-L-N;
修改强>
如果存在NaN,请将其用于M
而不是上述内容:
M = ~isnan(A)-L-N;
答案 1 :(得分:2)
q = prctile(A, [25,75,100])
5 15 15
30 50 35
40 70 50
我们可以使用bsxfun
查找以下各点之下的所有数字:
B = bsxfun(@le, A, permute(q, [3,2,1]);
现在你需要将每个矩阵(沿着第三个维度)与前一个矩阵的~
(即B(:,:,2) = B(:,:,2).*~B(:,:,1)
)进行累加,你可以用循环做或者你可以对它进行矢量化像这样:
N = cat(3, ones(size(B,1), size(B,2)), ~B(:,:,1:end-1))
B.*N
返回:
ans(:,:,1) =
1 1 0
0 0 0
0 0 0
0 0 1
ans(:,:,2) =
0 0 0
1 1 1
1 0 1
0 1 0
ans(:,:,3) =
0 0 1
0 0 0
0 1 0
1 0 0
如果要查找不同百分位数的索引,此方法可以非常容易地扩展:
p = [25, 75, 100];
q = prctile(A, p);
B = bsxfun(@le, A, permute(q, [3,2,1]);
N = cat(3, ones(size(B,1), size(B,2)), ~B(:,:,1:end-1))
B.*N
因此,如果您想在五分位数中使用它,只需将p
更改为[20 40 60 80 100]