用matlab进行xlsx表格的提取和操作
用于提取并操作xlsx表格
在学习数学建模的时候,我们会遇到大数据问题,这类问题通常需要进行数据预处理,下面是我总结的一些预处理经验。数据预处理通常分为缺失值和异常值的检测与处理、数据标注、数据降维三个步骤。本文我们将以2020年全国数学建模竞赛C类题为例,讲解xlsx表格的提取与分类。1.数据提取
使用函数提取数据。
函数语法:
数字 = ()
数量 = (,表)
数字 = (,)
数字 = (,表,)
数字 = (,工作表,,'基本')
[数字,txt,原始] = (___)
___ = (,-1)
[num,txt,raw,] = (,sheet,,''
:需要提取的文件名(也可以是文件路径);num:返回的 类型的数据矩阵(字符串数据在此矩阵中显示为NaN);sheet:需要提取的表格页码或者页面名称; :需要提取的数据范围,使用Excel范围语法,如'A1:C3';txt:以单元格数组的形式返回文本字段,数据类型的元素为单元格中的空值;raw:以单元格数组的形式返回数值数据和文本数据
待处理表的预览
观察上表,其中既有文本数据,也有数值数据,所以我们使用 [num,txt,raw] = (___) 来提取表中的数据,以确保可以提取所有数据。
代码:[num,txt,raw] = ('附件1:123家有信用记录公司数据.xlsx',2)
2. 删除垃圾数据
从表中取出所有数据后,我们可以使用矩阵语法对其进行操作。我们可以看到表中最后一列包含作废发票,因此我们要删除它们。基本思路是找到第八列中的所有“作废发票”,返回它们的行索引,然后删除这些行。
提取第八列
因为raw第一行是对应列的标题,所以我们从第二行开始
L8 = raw(2:end,8)
找到第八列中的元素“ ”
tf = strcmp('作废发票',L8);
该函数可以判断字符串数组中的元素是否与给定的字符串完全相同,如果完全相同则返回1,否则返回0。tf是一个与L8大小相同的矩阵。
返回相应行索引并清除
index = find(tf==1);
%去除作废发票
raw(index+1,:) = [];
find 函数可以返回满足括号中关系的元素的索引。由于我们从第二行开始搜索,因此将 index+1 行设置为 [ ] 相当于删除 index+1 行。删除后,单元格数组的大小也会发生变化。
3.数据分类
数据分类主要有两个方面,一个是公司分类,一个是日期分类。为了方便,我们将raw的每一列复制到一个变量中。
L1 = raw(2:end,1);L2 = raw(2:end,2);L3 = raw(2:end,3);L4 = raw(2:end,4);
L5 = raw(2:end,5);L6 = raw(2:end,6);L7 = raw(2:end,7);L8 = raw(2:end,8);
查找所有公司名称
L1对应第一列,即公司代码列
uni = unique(L1);
函数返回字符串数组中所有不同的字符串,由于是内置函数,所以字符串出现的顺序与原数组不同,后面写代码的时候请注意这一点。
找到所有公司名称对应的行号,并将它们存储在单元格数组中
compid = cell(length(uni),1);
for i = 1:length(uni)
tf = strcmp(uni(i),L1);
index = find(tf==1);
compid{i} = index;
end
单元格数组的赋值应该使用花括号{ },单元格数组值的提取也应该使用花括号。返回值是数据类型或者新的单元格使用括号()。
查找每个公司和每个月的行号并将其存储在新单元格中
L3 对应的是日期列,通过函数可以知道日期跨度为 4 年,因此我们创建一个 12x4=48 个列单元格,用于存储从 2016 年 1 月到 2019 年 12 月的行号。
Et = cell(length(uni),4*12);
%循环公司的坐标表
for i = 1:length(uni)
for j = [2016 2017 2018 2019];
for k = 1:12
idcp = compid{i};
logbool = strncmp(L3(idcp),sprintf('%d%s%d%s',j,'/',k,'/'),7);
index = find(logbool==1);
Et{i,(j-2016)*12+k} = index;
end
end
end
函数可以连接数字和字符串组,功能和函数类似,但是可以指定匹配字符串的长度,如上面的代码规定,如果前7个字符相同,则返回1。
4. 图像绘制
到此我们已经有了所有公司的目录,以及所有公司不同月份的目录,如何使用这些目录才是关键,接下来我们按照时间序列,简单画出一个公司不同月份的总额和纳税总额的变化曲线。
新建一个.m文件,创建要查找的公司对象,并在公司名称单元格中找到其位置
在这里我想查找有关公司代码“E17”的信息
company = 'E17';
id = find(strcmp(uni,company)==1);
创建两个数组分别存储每月总金额和税费总额
L5对应金额栏,L6对应税额栏
Tolmm = zeros(48,1);%金额,按月来计
Tolsm = zeros(48,1);%税额,按月来计
t1 = [L5{compid{id}}];
t2 = [L6{compid{id}}];
for i = 1:48
Tolmm(i) = sum(t1(Et{id,i}));
Tolsm(i) = sum(t2(Et{id,i}));
end
绘制折线图
plot(1:48,Tolmm,'-',1:48,Tolsm,'.-');
legend([company '的发票金额'],[company '的发票税额'],'location','northwest');
xlabel('时间/月');ylabel('金额/元');
效果展示:
本文的文档及源代码地址