|
+ A7 N+ `4 }, n8 r- m( F 最近一段时间,工作上花了不少时间用MATLAB处理工厂下线的数据,数据庞大不说,复杂度也高,各种推算和统计 2 S9 L+ P$ h& g9 v. e" o0 A# h/ @
所以今天我打算总结一下,平时我在用MATLAB做数据分析时常用的几个小技巧 2 k' F8 m( S; O9 ?' b2 m
正好全国大学生数学建模竞赛下周就要开始了,希望今天的分享对参赛的朋友有所帮助
+ f+ i: Y5 d8 o8 B0 x 虽然不知道到时候会有哪些选题,但是能肯定的是,不管是什么题目,都离不开数据分析,这是唯一比赛前能好好准备的 1 B+ q4 _: j5 g: {, g+ v, g# ^
1. 数据类型的转换
0 a! W9 U8 G" y- H' z! i 有一类问题,不论你MATLAB水平如何,平时写代码的时候多少总会遇到,就是数据类型不一致,需要转换 1 [4 X5 h4 A% o' v
至于什么是数据类型,这个问题我就不科普了,大家可以直接在MATLAB命令栏“doc 数据类型”
* i' M2 f; ~$ Y / Z& r+ `, D3 v" c) C
通常在数据转换这个问题上,涉及到的比较常见几种的数据类型有double,char,cell,struct ! z) W8 I% `: z. Y) s
我给大家准备了一张数据类型转换的关系图,用class判断一下转换前的两种数据类型,然后按照下面这张图处理就完事了 + W! ]# [* S" B7 M6 @
/ K ^+ s; c C. J
2. 字符串的对比 3 `. T! [: M4 H' U
第二个经常需要处理的问题是,字符串的对比
b% s% b6 Y% L0 O. n 这里不单单指的是字符串,还包括cell元胞里面的字符串定位
: [7 K) w* P/ X9 e- p% [# z 如果单纯只是字符串的话,要判断两个字符串是否相同,strcmp函数可以实现对比 @* v* Z2 e0 ?! [3 Y& O+ s
strcmp(abc,abc) , m2 P3 k7 h8 k8 G1 U8 }4 ^2 {' G
判断字符串中是否包含某种字符串,可以使用contains函数
1 Z8 }; \+ L: @9 T+ p4 X* _ contains(abc,ab) 9 F$ K1 P$ K* O' b7 u
判断字符串中在哪几位出现某种字符串,可以使用regexp函数
, ~8 t$ z( n+ y$ B, M: k- d regexp(abac,a) ' W8 W' S% k. L" F
更常碰到的场景是,在cell元胞里面判断字符串,比如维度1x1000的cell中,定位哪几个cell里面的字符串是‘abc’,还是通过strcmp实现对比,再通过find定位 . ]5 I9 b) q& E. T1 f
a = strcmp(Cell_variable,abc);; b, M* z0 G( B
b = find(a == 1)
' k5 b/ E! v/ h# M( V 同样,要判断这1x1000的cell中,定位哪几个cell中的字符串,带有‘ab’,可以使用contains函数,再用find定位
' n# \0 j) ]1 v a = contains (Cell_variable,ab);
8 Y2 N$ g* [8 w; | b = find(a == 1)
# U- K8 [4 A) n8 I 掌握上面这两点,在平时处理cell的字符串,基本上就够用了
$ v$ w& G' g& z3 L% F; @ 3. 文件的读取写入
0 E3 D% i9 W% Y: o5 [ 文件的读取写入同样非常重要,在数据分析过程中,对应着信息的获取和数据处理结果的输出
, S( O4 A* F0 I+ W5 M* T) d/ R mat, txt, excel是平时最常碰到的文件类型 0 T/ @4 p' I2 f, v9 u! I4 j
mat就不用多说了,MATLAB中的一种文件类型,用于存储workspace中的变量,在数据分析过程中,可以经常把运算结果或中间阶段的数据,作为mat进行保存 2 _) T$ n; z4 I
加载mat文件,用的是“load 文件名”命令,也可以双击mat文件,保存mat文件,用的是“save 文件名”命令,也可以workspace右键保存
2 I% g. g" k, ~, R& {* j: j txt的读取方式有非常多,网上也有各种各样的介绍,我就介绍两种最常用,也是目前我一直在用的两种方法 ; E7 y1 y% M( ?7 _8 W+ R
第一种是通过importdata(‘test.txt’)命令,读取的结果是一个多行一列的cell元胞,后续的数据处理也就方便了,cell里面的字符串定位处理在前面也已经介绍过
+ ?% Y& b% V% K6 T# N9 G; E 另一种方法是,通过MATLAB工具条里的“导入数据”按钮,这种方法的一个好处是,导入过程中有很多非常人性化的设置,比如数据的分隔,范围定义,数据的输出类型等等 6 t1 g+ o$ n/ S- S, ^3 n
导出的选择也有不少,可以选择直接导出到workspace,也可以选择生成脚本或者是function,方便同类型文本的重复使用,对于不太喜欢写脚本导入数据的朋友,我比较推荐这种方式 & s% k( d0 O2 k) u6 p
8 G1 I9 |7 m/ b6 x, j9 L! [- K4 E `, z5 Y, J% c- R/ J
% x7 w& S' R/ ?- L6 h1 u" H6 j txt的写入,可以通过fopen,fprintf,fclose实现,基本上我所有GUI中关于代码生成的功能,都是通过这个方式将代码写入m脚本的,给大家举一个简单的txt写入的例子代码 0 H1 R; G [% o6 h9 u5 g! U
fid = fopen(test.txt,wt);
1 `4 v( |/ ]! u6 o- C& `* z fprintf(fid,test1\n);$ o# p* m6 ?( D8 M5 D. `% W, a, R
fprintf(fid,test2\n);+ L& I/ x; c" F
fclose(fid); # t/ e0 i' v' q. V2 E
关于txt的读取写入,我再多介绍一点,txt是文本文件中的一种,就是那种右键打开能读得懂的文件。类似的文本文件还有很多,像m文件,mdl模型文件,dcm文件,c代码等等,只要是文本文件,都可以用txt处理的方式,对目标文件进行读取写入。
' ?) x& N6 H8 I" X 最后讲一下Excel读取写入的问题,常写MATLAB脚本的朋友,对xlsread和xlswrite肯定不陌生,对应的是Excel的读取和写入
3 r# r; ]# q# s1 |7 J( m [num,txt,raw] = xlsread(filename,sheet,xlRange)
1 t& Z9 E7 E! z( a" K xlswrite(filename,A,sheet,xlRange) 1 r7 Y$ T; ^" J
但是目前MATLAB官方已经不推荐使用这两种方式了,替代的函数是readtable和writetable
8 \; e" R ^3 ~, B1 z T = readtable(filename)7 L# b% r& D- V8 K
writetable(T,filename)
$ x1 ^0 R, U; q
7 u! x& F. \) W3 x5 | 如果数据是cell元胞的话,替代的函数是readcell和writecell
) f0 b( n; @$ b T = readcell(filename)( z, q$ u: ]2 h+ j
writecell(T,filename)
4 {+ m0 I( W3 `4 F 大家根据自己的个人习惯选择其中一种方式,两种方式在功能实现上目前并没有太大区别
F" w( n- V# k! F r 4. 数据可视化 - y5 Z: ~1 R+ P2 f. S+ H# D' O
数据可视化,结果的呈现,也是数据分析过程中至关重要的一环
( y7 O. u+ O$ W5 n" j 像大家非常熟悉的函数plot,就可以用来画曲线图,但是有时候仅仅曲线图并不足以来呈现结果,还需要用到比如像三维图,柱状图,饼状图,蜡烛图等等 ! U8 O# u3 k2 X; \' I& `- S6 G
这部分我并不打算给大家罗列各种图形对应代码命令,大家也没必要刻意地去死记这些代码,安利一个非常通用的方法
/ @; D* }: Z% a" u; d 在选择需要可视化的数据之后,在MATLAB工具条的绘图窗口,选取你喜欢的图形,就能生成你需要的结果图了 7 w- b7 A1 N6 h
( P4 D1 ?% @# l& `: Y* b 不过,至于图片的细节,像title,legend,网格,还是需要自己微调,但这都不是事,再安利大家一个简单的方法,完全不用上网去搜 % v7 M4 H ]/ I! _& O( ?) F
在生成窗口中,点击属性检查器,然后根据自己的需要完善图片的细节,最后通过生成代码,就能看到这部分作图操作的原始代码了,大家也能在代码的基础上再微调,或者复用
- v$ q# c. R# [9 u& t8 H 7 b& H& K$ Q, V5 V+ A" D- G
; _* f! N/ P- T: ]
* E o0 Q. } P
5. 数据处理的常用函数
5 J6 G: P* I% B& J3 U 关于数据处理的函数,像max,min,mean,std这些函数都是比较常用的函数,分别是最大值,最小值,平均值,标准差 ' ]( A* \7 X; g: ?; C
再安利大家几个平时我在处理数据时最常用的几个函数
C* y: V/ D$ S/ B: _ U 第一个是unique函数,可以把数据中重复的数据删去,保留唯一值。unique这个函数不仅仅对数值矩阵有效,在cell中同样起作用 " Y! s/ V, w7 v+ Y
C = unique(A)
8 \' k/ z3 P; l; w unique还有一些拓展的语法和功能,有兴趣的朋友可以在MATLAB文档中查看,不过光这个基本功能,就已经非常够用了 8 P" X) Y! y0 F1 }* b2 {# p% a
第二个要推荐的函数是排序,sort和sortrows,两种函数都有排序的功能,但是使用场景不太一样 ! F0 \4 P5 c" e& d% C3 f( T
sort的功能是,将矩阵或者cell中的每行或者每列进行升序或降序排列,其中A代表待处理的矩阵或cell数据,dim的选择有1和2,分别代表对每列和每行进行排序,direction的选择有ascend或 descend,分别代表升序和降序
! _( ]/ U2 h2 G/ R B = sort(A,dim,direction)
2 i# D1 f! s5 l, t3 \4 U sortrows的功能是,将矩阵或者cell根据某一列进行升序或降序排列,其中A代表待处理的矩阵或cell数据,column代表根据第几列进行排序,direction的选择有ascend或 descend,分别代表升序和降序
9 U K) ]% Z3 D$ a9 y6 ~ B = sortrows(A,column ,direction) # Y- a0 |( j6 @6 c
最后推荐的一个函数是tabulate,非常强的一个命令,可以实现对数据的统计分析,输出的结果有三列,分别是去重后的数据,出现的次数,已经对应的百分比 4 k6 }. D) u# g9 l% `
再结合sortrows对tabulate生成的结果进行排序,就很容易获得各个数据根据频率进行排序的结果 & L# r+ Z% x7 \- O) D5 s' r3 X6 G
: W B6 X1 r$ D. y2 `* T6 ] t7 f9 c
除了上面提到的几个日常比较常用的函数,还有一些我非常推荐的函数,平时我用的不太多,但是如果用到的时候找不到会很抓狂的那种 # _; U+ o8 m5 K9 i+ _# x4 l" |
比如reshape,可以根据自己的需求对数组进行重构 8 {1 x0 }. [# H/ X+ a
isequal,可以用来确定两个数组是否相等 ' p# X7 r. T4 u" M5 Y# I
datenum,datestr相信大家比较熟悉,可以将日期转换成序列值和字符,平时在处理时间相关数据的时候,还可以考虑用years,days,hours,minutes,seconds等等来计算持续时间
, a+ X' R' |! h5 s) E7 x 常用函数这部分内容就介绍到这,其实还有很多非常赞的函数,欢迎大家把自己喜欢的函数发到评论区
6 a) \! k5 Z) d* V( ~& l
( t9 g; p! `. \8 T% K" Q& [ 6. 数据爬取
( W: t7 l3 g0 W" \8 t$ \ y! } 数据爬取部分,其实我想讲的是爬虫,不过也不能算数据分析的技巧,我讲这部分内容,更多的是出于建模竞赛的原因
9 L( ]0 H* x5 d8 U4 q1 H 建模、仿真和验证,其实是需要数据的支持的。脱离实际意义的建模,靠拍脑门做出来的结果,都是不提倡的
5 a# {' e/ v/ i; q3 y 最简单的情况,如果有现成的数据文件,可以根据今天聊到的第三部分,读取数据文件之后进行分析 + i' p3 @; c: P* N0 X, P. _
如果没有这些数据,我推荐大家使用MATLAB读取网页的函数webread进行数据爬取
7 l8 g3 n' X2 @% L* X$ Y( }# n data = webread(url)
5 d7 Z Q: C# a! }' u% t `% o 爬取到数据之后,再通过regexp函数正则法处理网页数据
' |2 O! Q1 n$ R4 M- V 这部分聊的比较浅,但也很难三两句话把爬虫讲完,推荐大家一个相关的MATLAB爬虫视频,讲的是我之前用MATLAB爬取B站,视频很短,一共7分钟,大家一边看一边跟着做练习,基本上半个小时也就全整明白了(知乎不给放二维码,有需要的朋友,直接上B站搜打浦桥程序员吧) ' ~, m, H/ @: p* Y0 K8 w- _
7. 薅系列工具 & g3 B. s8 L$ c, V# L/ a
最后一部分要安利给大家的是,由我自己开发的薅系列工具 3 d, G0 ]& B0 [/ F- F x+ N1 c* b
目前反响最好的是薅曲线(HaoCurve),从图片中提取曲线的原始数据。之前不少参加过建模竞赛的朋友经常私信说,拿薅曲线来做结果验证特别管用
' ~/ }+ [+ p( U$ t2 ?+ c4 X) { 虽然这个工具我平时用到的不太多,不过就冲8000多的下载量来说,我还是很推荐的。需要的朋友,戳下方的文章链接获取工具下载方式 ! W! O A$ J4 \* A1 a
* z& q- }, n! |( ^. t/ `. E
4 U( L" Z! S9 z
) H: m/ v- M6 z- J7 T/ [ 1 F# y; G- D1 E2 l6 w, U7 R r
我个人用的比较多的是另外两款工具,一个是薅文件(HaoFile),里面的历史代码检索功能很强大,可以大大减少找代码写脚本的时间,在数据分析过程中,很多脚本和功能都是可以复用的,有需要的朋友,戳下方的文章链接获取工具下载方式 $ {2 f7 C. x5 @/ @& r0 s
; ^. G* W2 Q- L3 K5 P/ [ 打浦桥程序员:背几段MATLAB代码就那么难吗? ! Q" ]% ^! K/ {
2 u8 [ N, p4 N1 q4 o
, c8 h2 v$ t* c/ z$ @
/ f8 X5 o% P8 t f3 e
+ M$ f3 o) ~- z% k+ E: T. t( X
另一款工具是薅模版(HaoTemplate),如果最终数据分析的交付文档有格式上的要求,薅模版能就发挥它的作用,可以生成特定格式的Excel或Word模版代码,这可比自己手动去调格式方便很多,有需要的朋友,戳下方的文章链接获取工具下载方式 # p; W( M+ E8 d3 | W) ^! s
, m5 }3 G w5 G7 ~! c0 {; |) O
' z% {6 ?+ H R0 E0 K
$ m9 V) P/ V( Z- n( J
* v) g7 [3 l/ E 薅系列工具还有很多,不过在数据分析这部分,我最推荐的是这三款工具
7 K. \4 Y* b0 d" B$ o, b( u
% l, \& \8 g, M7 Y- h' t' q 不知觉间,写了这么多字 # I6 R% q/ c: |
今天总结的小技巧,未必是最适合大家的方法,但确实是我这些年养成的一些处理习惯
. I- K. h2 | N$ a* b 希望今天总结的方法,对大家平时的工作学习有所帮助,当然大家如果有更推荐的小技巧,欢迎在评论区补充
1 ^. r S5 C: s2 N 如果你也对MATLAB感兴趣的话,欢迎关注我的微信公众号“打浦桥程序员”
# y$ K) W* c* y ^) \% V
4 Q7 x- ]( x( w5 X5 P& _7 ^* R1 \- N, B! P
2 N; P+ ~2 R" Y; c5 N
. T C1 @6 V& @, Z7 j |