混合数据类型 Matlab 表

Mixed Data Types Matlab Tables

我希望对以下数据使用 makeValidName 函数:

Id  Val Random          Desc
a   1.1 0.036835624 Bread Cheese
b   2.2 0.020442492 Fish Bread
c   -3.3    0.020050676 Cheese Fish
d   #N/A    0.017619332 Bread Cheese
e   -5.4    0.014973153 Fish Bread
f   6.6 0.014648887 Cheese Fish
g   -7.6    0.014071844 Bread Cheese
h   8   0.014013118 Fish Bread

然而,当我导入 table(使用 readtable 从 xlsx 读取)时,它看起来像这样:

输入数据 =

 Id             Val              Random          Desc     
____    ____________________    ________    ______________

'a '    '1.1'                   0.036836    'Bread Cheese'
'b'     '2.2'                   0.020442    'Fish Bread'  
'c'     '-3.3'                  0.020051    'Cheese Fish' 
'd'     'ActiveX VT_ERROR: '    0.017619    'Bread Cheese'
'e'     '-5.4'                  0.014973    'Fish Bread'  
'f'     '6.6'                   0.014649    'Cheese Fish' 
'g'     '-7.6'                  0.014072    'Bread Cheese'
'h'     '8'                     0.014013    'Fish Bread'  

如何防止它将 Val 中的条目从数字转换为字符串?这使得无法使用 makeValidName。我需要在所有行和列中应用 makeValidName,因为 table 非常大,单独命名适当的列是不可行的。那么实现这一目标的最优雅方式是什么?

当前代码:

varnames = inputData.Properties.VariableNames;
for ii = 1:length(varnames)

inputData.(varnames{ii})= matlab.lang.makeValidName(inputData.(varnames{ii}));

end

产生错误:

Error using matlab.lang.makeValidName (line 72) First input must be string or vector cell array of strings.

并在 Val:

等列中产生不良结果

输入数据 =

Id            Val             Random         Desc     
___    __________________    ________    _____________

'a'    'x1_1'                0.036836    'BreadCheese'
'b'    'x2_2'                0.020442    'FishBread'  
'c'    'x_3_3'               0.020051    'CheeseFish' 
'd'    'ActiveXVT_ERROR_'    0.017619    'BreadCheese'
'e'    'x_5_4'               0.014973    'FishBread'  
'f'    'x6_6'                0.014649    'CheeseFish' 
'g'    'x_7_6'               0.014072    'BreadCheese'
'h'    'x8'                  0.014013    'FishBread'

因为在中间使用 Excel 似乎更让人头疼。我建议使用 basic 模式,这将减少一些解析错误。

来自 the documentation:

basic mode is the default for systems without Excel for Windows. In basic mode, readtable:

  • Reads XLS, XLSX, XLSM, XLTX, and XLTM files only.
  • Does not support the 'Range' name-value pair argument when reading XLS files.
  • Imports all dates as Excel serial date numbers. Excel serial date numbers use a different reference date than MATLAB® date numbers.

这使我们能够利用 TreatAsEmpty 名称-值对参数,因为它将正确解析数字列。

inputData = readtable('test.xlsx', 'Basic', 1, 'TreatAsEmpty', '#N/A');

示例案例returns:

inputData = 

    Id     Val      Random          Desc     
    ___    ____    ________    ______________

    'a'     1.1    0.036836    'Bread Cheese'
    'b'     2.2    0.020442    'Fish Bread'  
    'c'    -3.3    0.020051    'Cheese Fish' 
    'd'     NaN    0.017619    'Bread Cheese'
    'e'    -5.4    0.014973    'Fish Bread'  
    'f'     6.6    0.014649    'Cheese Fish' 
    'g'    -7.6    0.014072    'Bread Cheese'
    'h'       8    0.014013    'Fish Bread'

理论上这应该意味着数值数据列是 double 数组,而字符串保留在 cell 数组中。因此,要使用 matlab.lang.makeValidName you can test each column with iscell 来查看它是否是元胞数组:

varnames = inputData.Properties.VariableNames;
for ii = 1:length(varnames)
    if iscell(inputData.(varnames{ii}))
        % If they're strings they're in a cell array
        inputData.(varnames{ii})= matlab.lang.makeValidName(inputData.(varnames{ii}));
    end
end

哪个returns:

inputData = 

    Id     Val      Random         Desc     
    ___    ____    ________    _____________

    'a'     1.1    0.036836    'BreadCheese'
    'b'     2.2    0.020442    'FishBread'  
    'c'    -3.3    0.020051    'CheeseFish' 
    'd'     NaN    0.017619    'BreadCheese'
    'e'    -5.4    0.014973    'FishBread'  
    'f'     6.6    0.014649    'CheeseFish' 
    'g'    -7.6    0.014072    'BreadCheese'
    'h'       8    0.014013    'FishBread'