Matlab 具有两个索引数组的cellfun
我有一个N乘1维的大细胞。每行可以是一个字符串,也可以是一个双精度字符串。一个字符串是一个变量名,在下一个字符串(另一个变量名)出现之前,顺序双精度是它的值。例如:Matlab 具有两个索引数组的cellfun,matlab,Matlab,我有一个N乘1维的大细胞。每行可以是一个字符串,也可以是一个双精度字符串。一个字符串是一个变量名,在下一个字符串(另一个变量名)出现之前,顺序双精度是它的值。例如: data = { var_name1; val1; val2; val3; val4; val5; var_name2; val1; val2; var_name3; val1; val2; val3; val4; val5; val6; val7} 等等。我想把数据单元分成三个单元;{var_name和它的5个值},{var_n
data = {
var_name1;
val1;
val2;
val3;
val4;
val5;
var_name2;
val1;
val2;
var_name3;
val1;
val2;
val3;
val4;
val5;
val6;
val7}
等等。我想把数据单元分成三个单元;{var_name和它的5个值},{var_name和它的2个值},{var_name和它的7个值}。我尽量不循环,发现矢量化和cellfun一起工作非常好。可能吗?数据单元格有近百万行。
cellfun
用于将函数应用于单元格的每个元素
当您像这样将多个参数传递给cellfun
时,它会接受data
的i
第个参数、indx_first
和indx_last
,并在匿名函数中使用它们。将这些变量代入,对于数据中的每个元素x
,函数的计算结果为x(y:z)
。换句话说,您正在执行数据{i}(y:z)
,即索引单元格数组的实际元素,而不是索引单元格数组本身。我认为那不是你想要的。确实需要数据{y:z}
,对于indx_first
和indx_last
中相应元素给出的每个(y,z)
对,对吗
如果确实是这样,我看不到解决问题的矢量化方法,因为每个“变量”都有不同的大小。但是你知道你有多少个变量,也就是indx\u的大小。所以我会预先分配,然后循环,就像这样:
>> vars = cell(length(indx_first), 2);
>> for i = 1:length(vars)
vars{i, 1} = data{indx_first(i) - 1}; % store variable name in first column
vars{i, 2} = [data{indx_first(i) : indx_last(i)}]; % store data in last column
end
最后,您将得到一个包含2列的单元格数组。每行的第一列是变量的名称。二是实际数据。即
{'var_name1', [val1 val2 val3 val4 val5];
'var_name2', [val1 val2];
.
.
.
我相信下面这些应该是你想要的。主要部分是用来计算出每行对应的名称,然后建立每个名称的列表
% Make some data
data = {'a'; 1; 2; 3;
'b'; 4; 5;
'c'; 6; 7; 8; 9;
'd';
'e'; 10; 11; 12};
% Which elements are the names?
isName = cellfun(@ischar, data);
% Use CUMSUM to work out for each row, which name it corresponds to
whichName = cumsum(isName);
% Pick out only the values from 'data', and filter 'whichName'
% for just the values
justVals = data(~isName);
whichName = whichName(~isName);
% Use ACCUMARRAY to build up lists per name. Note that the function
% used by ACCUMARRAY must return something scalar from a column of
% values, so we return a scalar cell containing a row-vector
% of those values
listPerName = accumarray(whichName, cell2mat(justVals), [], @(x) {x.'});
% All that remains is to prepend the name to each cell. This ends
% up with each row of output being a cell like {'a', [1 2 3]}.
% It's simple to make the output be {'a', 1, 2, 3} by adding
% a call to NUM2CELL on 'v' in the anonymous function.
nameAndVals = cellfun(@(n, v) [{n}, v], data(isName), listPerName, ...
'UniformOutput', false);
既然每个“循环”的大小为1,那么indx_last
对每个“循环”都是一样的吗?