用 Linux 处理数据

这一节记录下做数据处理时用到的一些 Linux 和 命令行技巧。大部分命令在 OS X 系统也适应。

为什么使用 Linux 和命令行

一提到 Linux,许多人都会说到“自由”,但我不认为他们都知道“自由”的真正涵义。“自由”是一种权力, 它决定你的计算机能做什么,同时能够拥有这种“自由”的唯一方式就是知道计算机正在做什么。 “自由”是指一台没有任何秘密的计算机,你可以从它那里了解一切,只要你用心的去寻找。

你是否注意到,在电影中一个“超级黑客”坐在电脑前,从不摸一下鼠标, 就能够在30秒内侵入到超安全的军事计算机中。这是因为电影制片人意识到, 作为人类,本能地知道让计算机圆满完成工作的唯一途径,是用键盘来操纵计算机。

现在,大多数的计算机用户只是熟悉图形用户界面(GUI),并且产品供应商和此领域的学者会灌输给用户这样的思想, 命令行界面(CLI)是过去使用的一种很恐怖的东西。这就很不幸,因为一个好的命令行界面, 是用来和计算机进行交流沟通的非常有效的方式,正像人类社会使用文字互通信息一样。人们说,“图形用户界面让简单的任务更容易完成, 而命令行界面使完成复杂的任务成为可能”,到现在这句话仍然很正确。

-- The Linux Command Line

Linux 安装和配置

如果没有任何编程及命令行基础,推荐使用 Ubuntu,有经验后可转 Debian,包多,稳定。进入系统,安装下 Anaconda,基本的 Python 环境 & 数据工具箱便有了。

再进入终端仿真器,0S X 自带 Terminal,但推荐用 iTerm 2,Debian 是 Konsole,配置下 终极Shell 环境 Oh My ZSH!

sh -c "$(curl -fsSL https://raw.github.com/robbyrussell/oh-my-zsh/master/tools/install.sh)"

如果提示你没有安装相关的依赖包,那么则需先安装相关依赖包,比如 Ubuntu 则需要想安装 Git、和 zsh 等,

sudo apt-get install git zsh

再装个查看数据、转换数据的小工具 csvkit,

sudo apt-get install csvkit

至此,便可开始数据科学之旅了。

基础命令

很多数据问题都可以用命令行解决,而且有些可以解决的非常高效,前提你熟悉一些基础的。
入门级命令,无非这些:

pwd #打印出当前工作目录名
cd #更改目录
ls #列出目录内容
ls #列出目录内容
file #确定文件类型
less #浏览文件内容
cp #复制文件和目录
mv #移动/重命名文件和目录
mkdir #创建目录
rm #删除文件和目录
ln #创建硬链接和符号链接

上面的 # 号代表注释,没有任何意义

入门级命令太简单了,就不介绍了,如果从来没碰过命令行,不熟悉使用可以查看帮助,如ls --help,另外我推荐些好书。

重定向和管道符

若你有仔细看过推荐书的任何一本,并做了些许练习,那么你的命令行已经入门了。在介绍命令行处理数据前,我想先谈谈重定向和管道符,若要给 Linux 的符号们举行「频繁使用」比赛,那他们必定是冠军。

平常你在终端里输入ls -l,结果应该类似这样:

➜  Dropbox ls -l
total 704
drwxr-xr-x@ 19 Scott  staff   646B Apr  3 10:27 A.HighlyEffectiveSelf
drwxr-xr-x@  5 Scott  staff   170B Apr  3 09:28 B.CreativePleasure
drwxr-xr-x@ 10 Scott  staff   340B Apr  3 09:10 C.TheArtOfWork
drwxr-xr-x@ 11 Scott  staff   374B Mar 10 12:40 D.HistoricalMemory
drwxr-xr-x@ 12 Scott  staff   408B Apr  3 10:09 E.DataBank
drwxr-xr-x@ 19 Scott  staff   646B Apr  3 09:14 F.BambooBasket
drwxr-xr-x@  5 Scott  staff   170B Mar  9 12:34 G.Other
-rw-r--r--@  1 Scott  staff     0B Apr  3 07:58 Icon?
-rw-rw-r--@  1 Scott  staff   312B Apr  3 16:18 README.md

文件是文件名排序的,若加个管道符‘|’呢?

➜  Dropbox ls -l | sort
-rw-r--r--@  1 Scott  staff     0B Apr  3 07:58 Icon
-rw-rw-r--@  1 Scott  staff   312B Apr  3 16:18 README.md
drwxr-xr-x@  5 Scott  staff   170B Apr  3 09:28 B.CreativePleasure
drwxr-xr-x@  5 Scott  staff   170B Mar  9 12:34 G.Other
drwxr-xr-x@ 10 Scott  staff   340B Apr  3 09:10 C.TheArtOfWork
drwxr-xr-x@ 11 Scott  staff   374B Mar 10 12:40 D.HistoricalMemory
drwxr-xr-x@ 12 Scott  staff   408B Apr  3 10:09 E.DataBank
drwxr-xr-x@ 19 Scott  staff   646B Apr  3 09:14 F.BambooBasket
drwxr-xr-x@ 19 Scott  staff   646B Apr  3 10:27 A.HighlyEffectiveSelf
total 704

这里我加了‘|’ 和 ‘sort’ 命令,你会发现,文件的排序已经变了,变成了文件大小的排序。这个命令和简单解释为ls -l输出了文件排序结果,而 sort 则接受了这个结果,并把它重新按文件的大小进行了排序,所以 ‘|’起到的就是管道的作用,可以从标准输入读取数据,然后再把数据输送到标准输出。这个特性非常有用,意味着你可以进行非常复杂的操作。

而什么是重定向‘>’呢?你用命令行操作的结果正常是直接显示在屏幕上的,那还有别的方式吗?你试试:

ls -l > ex01.txt

你发现,没有任何动静,但工作目录多了一个 ex01.txt 的文件,查看下这个文件试试,

➜  Dropbox cat ex01.txt
total 704
drwxr-xr-x@ 19 Scott  staff  646 Apr  3 10:27 A.HighlyEffectiveSelf
drwxr-xr-x@  5 Scott  staff  170 Apr  3 09:28 B.CreativePleasure
drwxr-xr-x@ 10 Scott  staff  340 Apr  3 09:10 C.TheArtOfWork
drwxr-xr-x@ 11 Scott  staff  374 Mar 10 12:40 D.HistoricalMemory
drwxr-xr-x@ 12 Scott  staff  408 Apr  3 10:09 E.DataBank
drwxr-xr-x@ 19 Scott  staff  646 Apr  3 09:14 F.BambooBasket
drwxr-xr-x@  5 Scott  staff  170 Mar  9 12:34 G.Other
-rw-r--r--@  1 Scott  staff    0 Apr  3 07:58 Icon
-rw-rw-r--@  1 Scott  staff  312 Apr  3 16:18 README.md
-rw-rw-r--   1 Scott  staff    0 Apr  3 16:57 ex01.txt

输出结果已经在这个文件里面了,这就是重定向的特性,允许我们来重定义标准输出送到哪里,在‘>’符号后面接个文件名即可。这点是非常实用的,比如你处理完数据后,肯定希望保存到一个文件里面。另外要注意一点,‘>’会格式化原有文件的内容,所以如果你是添加内容,请采用‘>>’。

处理数据常用命令

行过滤

若拿到一个很大的数据后,你肯定不想立马查看所有数据,一没必要,而打开慢,而是想做下行过滤,看看一小部分。常用的行过滤命令有head、tail、seq

看前10行数据:

➜  ~ head user_service_time.txt
bid service_time    weekday hour    lasttime
17283201    2016-1-27 8:30:00   3   8   3.0
17283201    2016-1-29 9:00:00   5   9   3.0
17283201    2016-2-22 17:00:00  1   17  3.0
17283201    2016-2-25 16:00:00  4   16  3.0
17283201    2016-2-29 16:30:00  1   16  3.0
17283201    2016-3-2 9:00:00    3   9   3.0
17283201    2014-9-19 9:00:07   5   9
17283201    2014-11-3 13:00:00  1   13
17283201    2014-11-22 15:00:00 6   15  3

查看前5行:

head -5 filename

前 n 行:

head -n filename

tail 则跟 head 刚好相反,查看的是尾行。若需要指定某些行则可用 sedawk,如指定 4-6行,可用sed -n '4, 6p' filename,我这里为了好看,用 nl 命令先把行号打印出来。

➜  ~ nl user_service_time.txt | sed -n '4, 6p'
     4  17283201    2016-2-22 17:00:00  1   17  3.0
     5  17283201    2016-2-25 16:00:00  4   16  3.0
     6  17283201    2016-2-29 16:30:00  1   16  3.0
# 查看奇数行
➜  ~ nl user_service_time.txt | head |  awk 'NR%2'
     1  bid service_time    weekday hour    lasttime
     3  17283201    2016-1-29 9:00:00   5   9   3.0
     5  17283201    2016-2-25 16:00:00  4   16  3.0
     7  17283201    2016-3-2 9:00:00    3   9   3.0
     9  17283201    2014-11-3 13:00:00  1   13
# 偶数行
➜  ~ nl user_service_time.txt | head |  awk '(NR+1)%2'
     2  17283201    2016-1-27 8:30:00   3   8   3.0
     4  17283201    2016-2-22 17:00:00  1   17  3.0
     6  17283201    2016-2-29 16:30:00  1   16  3.0
     8  17283201    2014-9-19 9:00:07   5   9
    10  17283201    2014-11-22 15:00:00 6   15  3

列提取

行提取很简单,那么列提取应该如何做呢?

# 把所有缩进符号改为逗号(英文), 再重定向成 csv 文件, .txt 文件可用 cat,excel 文件则需 in2csv
cat user_service_time.txt | tr '/t' ',' > user_service_time.csv

# 看看前 3 行,有哪些列
➜  ~ head -3 user_service_time.csv | csvlook
|-----------+--------------------+---------+------+-----------|
|  bid      | service_time       | weekday | hour | lasttime  |
|-----------+--------------------+---------+------+-----------|
|  17283201 |  2016-1-27 8:30:00 |  3      |  8   |  3.0      |
|  17283201 |  2016-1-29 9:00:00 |  5      |  9   |  3.0      |
|-----------+--------------------+---------+------+-----------|
# 得知总共有 5 列提取后 3 列 的前 10 行看看
➜  ~ < user_service_time.csv csvcut -c 3-5 | head | csvlook
|----------+------+-----------|
|  weekday | hour | lasttime  |
|----------+------+-----------|
|   3      |  8   |  3.0      |
|   5      |  9   |  3.0      |
|   1      |  17  |  3.0      |
|   4      |  16  |  3.0      |
|   1      |  16  |  3.0      |
|   3      |  9   |  3.0      |
|   5      |  9   |           |
|   1      |  13  |           |
|   6      |  15  |  3        |
|----------+------+-----------|
# 也可以用 -C 来忽略某些行,如忽略 3-5 列的前5行。
➜  ~ < user_service_time.csv csvcut -C 3-5 | head -5 | csvlook
|-----------+----------------------|
|  bid      | service_time         |
|-----------+----------------------|
|  17283201 |  2016-1-27 8:30:00   |
|  17283201 |  2016-1-29 9:00:00   |
|  17283201 |  2016-2-22 17:00:00  |
|  17283201 |  2016-2-25 16:00:00  |
|-----------+----------------------|

grep 查找

# 基本用法是 grep data filename
➜  ~ head user_service_time.txt | grep 29
17283201    2016-1-29 9:00:00   5   9   3.0
17283201    2016-2-29 16:30:00  1   16  3.0

wc 基本统计

  • 统计行数 wc -l file
  • 统计单词数 wc -w file
  • 统计字符数 wc -c file
➜  ~ wc -l user_service_time.txt
    1244 user_service_time.txt
➜  ~ < user_service_time.txt | grep 2016-2 | wc -l
      55

sort 排序

  • -n 按数字进行排序
  • -d 按字典序进行排序
  • -r 逆序排序
  • -k N 指定按第N列排序
# 以第 1 列数字反向排序
➜  ~ < user_service_time.csv | sort -nrk 1 | head -4 | csvlook
|-----------------+-------------------+---+---+----|
|  29101041557001 | 2016-3-6 8:30:00  | 7 | 8 | 4  |
|-----------------+-------------------+---+---+----|
|  29101041557001 | 2016-3-13 8:30:00 | 7 | 8 | 4  |
|  29101041557001 | 2016-2-28 8:30:00 | 7 | 8 | 4  |
|  29101041557001 | 2016-2-21 8:30:00 | 7 | 8 | 4  |
|-----------------+-------------------+---+---+----|

其他

iconv cut past uniq 等工具也是极好的,只不过用的略少,具体的数据分析则用 Pandas 更方便些。其他的,想到再添加。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 213,558评论 6 492
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 91,002评论 3 387
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 159,036评论 0 349
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 57,024评论 1 285
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 66,144评论 6 385
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 50,255评论 1 292
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,295评论 3 412
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 38,068评论 0 268
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,478评论 1 305
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,789评论 2 327
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 38,965评论 1 341
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,649评论 4 336
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 40,267评论 3 318
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,982评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,223评论 1 267
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 46,800评论 2 365
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 43,847评论 2 351

推荐阅读更多精彩内容

  • linux资料总章2.1 1.0写的不好抱歉 但是2.0已经改了很多 但是错误还是无法避免 以后资料会慢慢更新 大...
    数据革命阅读 12,151评论 2 33
  • Ubuntu的发音 Ubuntu,源于非洲祖鲁人和科萨人的语言,发作 oo-boon-too 的音。了解发音是有意...
    萤火虫de梦阅读 99,217评论 9 467
  • 本文笔记源自这里——[实验楼]欢迎大家在下面交流其中有问题的地方喜欢请点收藏,每日更新(全部已亲自实践). 一. ...
    东皇Amrzs阅读 3,977评论 7 54
  • 我不说话 你以为我有话说 其实我只是不说话 我说话 你以为我不说话 其实我在说话 我难过 你看的出来 我窘迫 你也...
    五盘鸡阅读 129评论 0 0
  • 人生如戏 戏如人生 上善若水,心智宁静 浮生若梦,时光匆匆 阑珊处,一醉有倒影 霓虹外,点点数繁星 岁岁年年,年年...
    诗酒人生阅读 328评论 1 3