JupyterNotebook
他山之石
Jupyter Notebook的27个窍门,技巧和快捷键
http://www.raincent.com/content-85-7795-1.html?Yg=wKY
Jupyter Notebook 使用Python内核,原名 IPython Notebook。Jupyter notebook是Jupyter项目的产物——Jupyter这个名字是它要服务的三种语言的缩写:Julia,PYThon和R,这个名字与“木星(jupiter)”谐音。
1.快捷键
Jupyter在顶部菜单提供了一个快捷键列表:Help > Keyboard Shortcuts 。每次更新Jupyter的时候,一定要看看这个列表,因为不断地有新的快捷键加进来。另外一个方法是使用Cmd + Shift + P ( Linux 和 Windows下 Ctrl + Shift + P亦可)调出命令面板。这个对话框可以让你通过名称来运行任何命令——当你不知道某个操作的快捷键,或者那个操作没有快捷键的时候尤其有用。这个功能与苹果电脑上的Spotlight搜索很像,一旦开始使用,你会欲罢不能。
Jupyter笔记本有两种不同的键盘输入模式.
Mac OS X modifier keys: | |
---|---|
⌘: 命令 | ⌃: 控制 |
⌥: 选项 | ⇧: Shift |
↩: 返回 | ␣: 空格 |
⇥: Tab |
命令模式将键盘与笔记本级命令绑定在一起,并通过一个灰色的单元格边界显示,该边框为蓝色的左边框。
命令模式 | (按 Esc 生效) |
---|---|
↩: 进入编辑模式 | ⌘⇧F: 打开命令配置 |
⌘⇧P: 打开命令配置 | P: 打开命令配置 |
⇧↩: 运行代码块, 选择下面的代码块 | ⇧↩: 运行代码块, 选择下面的代码块 |
⌥↩: 运行代码块并且插入下面 | Y: 把代码块变成代码 |
M: 把代码块变成标签 | R: 清除代码块格式 |
1: 把代码块变成heading 1 | 2: 把代码块变成heading 2 |
3: 把代码块变成heading 3 | 4: 把代码块变成heading 4 |
5: 把代码块变成heading 5 | 6: 把代码块变成heading 6 |
K: 选择上面的代码块 | ↑: 选择上面的代码块 |
J: 选择下面的代码块 | ⇧K: 扩展上面选择的代码块 |
⇧↑: 扩展上面选择的代码块 | ⇧↓: 扩展下面选择的代码块 |
⇧J: 扩展下面选择的代码块 | A: 在上面插入代码块 |
B: 在下面插入代码块 | X: 剪切选择的代码块 |
C: 复制选择的代码块 | ⇧V: 粘贴到上面 |
V: 粘贴到下面 | Z: 撤销删除 |
D,D: 删除选中单元格 | ⇧M: 合并选中单元格, 如果只有一个单元格被选中 |
⌘S: 保存并检查 | S: 保存并检查 |
L: 切换行号 | O: 选择单元格的输出 |
⇧O: 切换选定单元的输出滚动 | H: 显示快捷键 |
I,I: 中断服务 | 0,0: 重启服务(带窗口) |
Esc: 关闭页面 | F: 查找并且替换 |
编辑模式允许您将代码或文本输入到一个单元格中,并通过一个绿色的单元格来表示 |编辑模式|(按 Enter 生效)| |-|-| |⇥: 代码完成或缩进|⇧⇥: 工具提示| |⌘]: 缩进|⌘]: 缩进| |⌘A: 全选|⌘Z: 撤销| |⌘/: 评论|⌘D: 删除整行| |⌘U: 撤销选择|Insert: 切换 重写标志| |⌘↑: 跳到单元格起始处|⌘↓: 跳到单元格最后| |⌘↓: 跳到单元格最后|⌥→: 跳到单词右边| |⌥⌫: 删除前面的单词|⌥⌦: 删除后面的单词| |⌘⇧Z: 重做|⌘⇧U: 重新选择| |⌃K: emacs-style line kill|⌘⌫: 删除光标左边线| |⌘⌦: delete line right of cursor|⌃M: 进入命令行模式| |Esc: 进入命令行模式|⌘⇧F: 打开命令配置| |⌘⇧P: 打开命令配置|⇧↩: 运行代码块, 选择下面的代码块| |⌃↩: 运行选中的代码块|⌥↩: 运行代码块并且插入下面| |⌃⇧Minus: 在鼠标处分割代码块|⌘S: 保存并检查| |↓: 光标下移|↑: 光标上移|
类似在线Python运行平台
# File中包含创建以及重命名脚本文件等常用功能
# Edit 主要是集中在对内容区中的cell的操作
# view视图用于设置显示或者隐藏toolbar以及设置cell的一些相关的视图属性
# insert纯粹对cell进行操作,上方或者下方插入cell单元
# cell主要是运行cell的操作,比如运行所有的cell单元,运行某一个cell单元或者是清空cell单元的所有的内容
# kernel 功能主要是重启核或者是切换核,jupyter notebooke不仅仅可用于python的展示,也可以切换为其他的语言核进行其他语言代码编辑与运行展示
# help中即是包含了jupyter notebook 的所有操作的帮助提示,非常有用。
# 什么是cell?
# cell表示一个块,对于程序单元每一次点击工具栏上的Run的button,就会执行鼠标所在的cell然后显示出结果
# 当然也可以选择一次性运行所有的cell 通过Cell->run all 实现
# 常用快捷键 :
# Enter : 转入编辑模式
# Shift-Enter : 运行本单元,选中下个单元
# Ctrl-Enter : 运行本单元
Esc + F 在代码中查找、替换,忽略输出。
Esc + O 在cell和输出结果间切换。
选择多个cell:
Shift + J 或 Shift + Down 选择下一个cell。
Shift + K 或 Shift + Up 选择上一个cell。
一旦选定cell,可以批量删除/拷贝/剪切/粘贴/运行。当你需要移动notebook的一部分时这个很有用。
Shift + M 合并cell
?在库、方法或变量的前面打上,即可打开相关语法的帮助文档
包括Numpy,Pandas,Scipy和Matplotlib等。
aistudio终端
https://aistudio.baidu.com/user/107326/120607/notebooks/120607.ipynb?redirects=1
$ pwd
/home/aistudio
$ python
Python 3.6.3 | packaged by conda-forge | (default, Nov 4 2017, 10:10:56)
[GCC 4.8.2 20140120 (Red Hat 4.8.2-15)] on linux
Type "help", "copyright", "credits" or "license" for more information.
>>> print('love')
love
>>>
关于调试代码
Notebook自带一个调试器, 叫The Python Debugger (pdb)
自动pdb调用已经打开
# 对, 它也是依赖Magic命令启动的.
# 理论上pdb是可以通过脚本形式来启动. 但是在Notebook中不行, 会造成阻断
%pdb
关于变量监控
你可以通过修改内核选项ast_note_interactivity,使得Jupyter对独占一行的所有变量或者语句都自动显示,这样你就可以马上看到多个语句的运行结果了。
数据集
作图
在notebook里作图,有多个选择:
- matplotlib (事实标准),可通过%matplotlib inline 激活 ,
- %matplotlib notebook 提供交互性操作,但可能会有点慢,因为响应是在服务器端完成的。 - mpld3 提供matplotlib代码的替代性呈现(通过d3),虽然不完整,但很好。 - bokeh 生成可交互图像的更好选择。 - plot.ly 可以生成非常好的图,可惜是付费服务。
Numpy
NumPy是使用Python进行科学计算所需的基本软件包。
网站:Website: https://www.numpy.org
文档:Documentation: http://docs.scipy.org/ 邮件列表:Mailing list: https://mail.python.org/mailman/listinfo/numpy-discussion
源代码:Source code: https://github.com/numpy/numpy 贡献: Contributing: https://www.numpy.org/devdocs/dev/index.html 错误报告:Bug reports: https://github.com/numpy/numpy/issues 报告安全漏洞:Report a security vulnerability: https://tidelift.com/docs/security
github地址:https://github.com/numpy
它提供:
一个强大的N维数组对象 复杂的(广播)功能 用于集成C / C ++和Fortran代码的工具 有用的线性代数,傅里叶变换和随机数功能
测试:
NumPy版本≥1.15要求 pytest NumPy版本<1.15需要 nose
运行测试 python -c ‘import numpy; numpy.test()’
Notebook四个-ipython
要想使用 Qgrid 渲染数据帧,开发者只需导入 Qgrid,然后将数据帧输入到
show_grid 函数:
import qgrid
qgrid_widget = qgrid.show_grid(df, show_toolbar=True)
qgrid_widget
这样,你可以对数据帧执行大量交互式操作:
* 添加和删除行;
* 筛选行;
* 编辑单元格。
OOPPPPPppppøøøˆπ“ππππœ∑´®†¥¨¨ˆåß©˙∆˚¬¬…≈˜µ≤≥÷¡™™£¢∞§¶••ªªº÷åßç√®´∑∑œ†¥¨¨ˆøøøø¨¨¨˙˙˙˚˚˜∆∆˜˚¬˜¥©ççååß≈®¥´®†´††¥¨ˆˆ¨dßßßçç√√√∑∑®®dsfˆˆˆˆøø˚˚øø
option + az
三、命令历史记录与输入输出
1、所谓的命令历史主要是上一篇文章中已经讲到的两个快捷键的使用,即Ctrl+P和Ctrl+N。还可以使用%hist魔术方法。
2、所谓的输入与输出主要是使用 _、__、_X、_iX,这里的X表示行号,在前面也已经讲过,这里就不重复了。
四、ipython与操作系统进行交互
ipython与操作系统的shell是联系的非常紧密的,我们可以直接在ipython中就实现在操作系统的shell中所做的事情,包括执行shell命令、更改目录、为shell提供别名、创建目录书签、将shell执行的结果保存在python的对象中 等等操作,下面进行一些常见的实例。
1、!cmd :在ipython中打开系统的cmd。这就相当于现在ipython已经变成了系统自带的cmd,若要回到ipython界面,可以再输入ipython,这就相当于在cmd中启动ipython
2、%pwd :返回当前ipython的工作目录
%cd newdirectory: 进入新的工作目录
%dhist :打印目录访问的历史
%env :以dict的形式返回系统的环境变量
11
IPython魔术命令
•%timeit
多次执行一条语句,并返回平均时间,%%timeit->多条语句
• %time
返回执行一条语句的时间,%%time->多条语句
• %reset
删除当前空间的全部变量
• %run *.py
在IPython中执行Python脚本
魔术命令+(?)显示文档
如:%time?
1.快捷键
高手们都知道,快捷键可以节省很多时间。Jupyter在顶部菜单提供了一个快捷键列表:Help > Keyboard Shortcuts 。每次更新Jupyter的时候,一定要看看这个列表,因为不断地有新的快捷键加进来。另外一个方法是使用Cmd + Shift + P ( Linux 和 Windows下 Ctrl + Shift + P亦可)调出命令面板。这个对话框可以让你通过名称来运行任何命令——当你不知道某个操作的快捷键,或者那个操作没有快捷键的时候尤其有用。这个功能与苹果电脑上的Spotlight搜索很像,一旦开始使用,你会欲罢不能。
几个我的最爱:
Esc + F 在代码中查找、替换,忽略输出。
Esc + O 在cell和输出结果间切换。
选择多个cell:
Shift + J 或 Shift + Down 选择下一个cell。
Shift + K 或 Shift + Up 选择上一个cell。
一旦选定cell,可以批量删除/拷贝/剪切/粘贴/运行。当你需要移动notebook的一部分时这个很有用。
Shift + M 合并cell.
2.变量的完美显示
有一点已经众所周知。把变量名称或没有定义输出结果的语句放在cell的最后一行,无需print语句,Jupyter也会显示变量值。当使用Pandas DataFrames时这一点尤其有用,因为输出结果为整齐的表格。
鲜为人知的是,你可以通过修改内核选项ast_note_interactivity,使得Jupyter对独占一行的所有变量或者语句都自动显示,这样你就可以马上看到多个语句的运行结果了。
In [1]: from IPython.core.interactiveshell import InteractiveShell InteractiveShell.ast_node_interactivity = "all"In [2]: from pydataset import data quakes = data('quakes') quakes.head() quakes.tail()Out[2]: lat long depth mag stations 1 -20.42 181.62 562 4.8 41 2 -20.62 181.03 650 4.2 15 3 -26.00 184.10 42 5.4 43 4 -17.97 181.66 626 4.1 19 5 -20.42 181.96 649 4.0 11Out[2]: lat long depth mag stations 996 -25.93 179.54 470 4.4 22 997 -12.28 167.06 248 4.7 35 998 -20.13 184.20 244 4.5 34 999 -17.40 187.80 40 4.5 14 1000 -21.59 170.56 165 6.0 119
如果你想在各种情形下(Notebook和Console)Jupyter都同样处理,用下面的几行简单的命令创建文件~/.ipython/profile_default/ipython_config.py即可实现:
c = get_config()# Run all nodes interactivelyc.InteractiveShell.ast_node_interactivity = "all"
3.轻松链接到文档
在Help 菜单下,你可以找到常见库的在线文档链接,包括Numpy,Pandas,Scipy和Matplotlib等。
另外,在库、方法或变量的前面打上?,即可打开相关语法的帮助文档。
In [3]: ?str.replace()
Docstring:
S.replace(old, new[, count]) -> str
Return a copy of S with all occurrences of substring
old replaced by new. If the optional argument count is
given, only the first count occurrences are replaced.
Type: method_descriptor
4.在notebok里作图
在notebook里作图,有多个选择:
- matplotlib (事实标准),可通过%matplotlib inline 激活 ,
- %matplotlib notebook 提供交互性操作,但可能会有点慢,因为响应是在服务器端完成的。
- mpld3 提供matplotlib代码的替代性呈现(通过d3),虽然不完整,但很好。
- bokeh 生成可交互图像的更好选择。
- plot.ly 可以生成非常好的图,可惜是付费服务。
5.Jupyter Magic命令
上文提到的%matplotlib inline 是Jupyter Magic命令之一。
推荐阅读Jupyter magic命令的相关文档
它一定会对你很有帮助。下面是我最爱的几个:
6.Jupyter Magic-%env:设置环境变量
不必重启jupyter服务器进程,也可以管理notebook的环境变量。有的库(比如theano)使用环境变量来控制其行为,%env是最方便的途径。
In [55]: # Running %env without any arguments
# lists all environment variables
# The line below sets the environment
# variable OMP_NUM_THREADS
%env OMP_NUM_THREADS=4
env: OMP_NUM_THREADS=4
7.Jupyter Magic-%run:运行python代码
%run 可以运行.py格式的python代码——这是众所周知的。不那么为人知晓的事实是它也可以运行其它的jupyter notebook文件,这一点很有用。
注意:使用%run 与导入一个python模块是不同的。
In [56]: # this will execute and show the output from
# all code cells of the specified notebook
%run ./two-histograms.ipynb
8.Jupyter Magic-%load:从外部脚本中插入代码
该操作用外部脚本替换当前cell。可以使用你的电脑中的一个文件作为来源,也可以使用URL。
In [ ]: # Before Running
%load ./hello_world.py
In [61]: # After Running
# %load ./hello_world.py
if __name__ == "__main__":
print("Hello World!")
Hello World!
9.Jupyter Magic-%store:在notebook文件之间传递变量
%store 命令可以在两个notebook文件之间传递变量。
In [62]: data = 'this is the string I want to pass to different notebook'
%store data
del data # This has deleted the variable
Stored 'data' (str)
现在,在一个新的notebook文档里……
In [1]: %store -r data
print(data)
this is the string I want to pass to different notebook
10.Jupyter Magic-%who:列出所有的变量
不加任何参数,%who命令可以列出所有的变量变量。加上参数str将只列出字符串类型的变量。
在[1]中:一=“为了钱”
二=“为了表演”
三=“现在就准备去猫走吧”
%wstr
一三二
11,Jupyter Magic-计时
有两种用作计时的jupyter magic命令:%% time和%timeit。当你有一些很耗时的代码,想要查清楚问题出在哪时,这两个命令非常给力。
仔细体会下我的描述哦。
%% time会告诉你细胞内部代码的单次运行时间信息。
在[4]中: _在范围(1000)中的%% time
导入时间
:
time.sleep(0.01)#睡眠0.01秒
CPU时间:用户21.5 ms,sys:14.8 ms,总计:36.3 ms
挂墙时间:11.6 s
%% timeit使用了Python的timeit模块,该模块运行某条语句100,000次(更改值),然后提供生成的3次的替代作为结果。
在[3]中:import numpy
%timeit numpy.random.normal(size = 100)
最慢的运行时间比最快的运行时间长7.29倍。这可能意味着正在缓存中间结果。
100000个循环,最佳3:每个循环5.5 µs
12.Jupyter Magic-writefile和%pycat:启动单元内容/显示外部脚本的内容
而%pycat功能相反,将外部文件语法高亮显示(以弹出窗口方式)。使用%% writefile magic可以保存单元的内容到外部文件。
在[7]中:%% writefile pythoncode.py
import numpy
def append_if_not_exists(arr,x):
如果x不在arr中:
arr.append(x)
def some_useless_slow_function():
arr = list()
for i in range(10000) :
x = numpy.random.randint(0,10000)
append_if_not_exists(arr,x) 在[8]中
编写
pythoncode.py:%pycat pythoncode.py
import numpy
def append_if_not_exists(arr,x):
如果x不在arr中:
arr .append(x)
def some_useless_slow_function():
arr = list()
for i in range(10000):
x = numpy.random.randint(
0,10000 )append_if_not_exists(arr,x)
13.Jupyter Magic-%prun:告诉你程序中每个函数消耗的时间
使用%PRUN +函数声明会给你一个按顺序排列的表格,显示每个内部函数的耗时情况,每次调用函数的耗时情况,以及累计耗时。
在[47]中:%prun some_useless_slow_function()
26324在0.556秒内调用函数
排序方式:内部时间
ncalls tottime每次调用cumtime每次调用文件名:lineno(function)
10000 0.527 0.000 0.528 0.000:2(append_if_not_exists)
10000 0.022 0.000 0.022 0.000 {method' mtint.RandomState对象的randint”
1 0.006 0.006 0.556 0.556:6(some_useless_slow_function)
6320 0.001 0.000 0.001 0.000 {方法'追加''列表'对象}
1 0.000 0.000 0.556 0.556:1()
1 0.000 0.000 0.556 0.556 {内置方法执行程序}
1 0.000 0.000 0.000 0.000 {'_lsprof.Profiler'对象的方法'禁用'}
14.Jupyter Magic-用%pdb调试程序
Jupyter有自己的调试界面Python调试器(pdb),因此进入函数内部检查错误成为可能。
PDB柯林斯中使用的命令见链接
在[]中:%pdb
def pick_and_take():
Picked = numpy.random.randint(0,1000)
提高NotImplementedError()
pick_and_take()
自动pdb调用已打开
-------------------------------------------------- -------------------------
()
中的NotImplementedError错误回溯(最近一次通话最后一次)
5引发NotImplementedError()
6
----> 7 pick_and_take()
中的pick_and_take()
3 def pick_and_take():
4 pick = numpy.random.randint(0,1000)
- ---> 5引发NotImplementedError()
6
7 pick_and_take()
NotImplementedError:
>(5)pick_and_take()
3 def pick_and_take():
4 pick = numpy.random.randint(0,1000)
----> 5引发NotImplementedError ()
6
7 pick_and_take()
ipdb>
15.末句函数不输出
有时候不让末句的函数输出结果比较方便,比如在作图的时候,此时,只需在该函数末尾加上一个分号即可。
在[4]中:
从matplotlib内联%matplotlib ,将pyplot导入为plt
import numpy
x = numpy.linspace(0,1,1000)** 1.5
在[5]中:#此处获得函数
plt.hist(x 的输出)
Out [5]:(
array([216.,126.,106.,95.,87.,81.,77.,73.,71.,68.]),
array([0.,0.1, 0.2、0.3、0.4、0.5、0.6、0.7、0.8、0.9、1。]),
)
在[6]中:#通过在末尾添加分号来抑制输出。
plt.hist(X);
16.运行壳牌命令
在笔记本内部运行外壳命令很简单,这样你就可以看到你的工作文件夹里有哪些数据集。
在[7]中:!ls * .csv
nba_2016.csv titanic.csv
pixar_movies.csv whitehouse_employees.csv
17.用LaTex的写公式
当你在一个降价单元格里写LaTex的时,它将用MathJax呈现公式:如
$$ P(A \ mid B)= \ frac {P(B \ mid A),P(A)} {P(B)} $$
18.在笔记本内用不同的内核运行代码
如果你想要,其实可以把不同内核的代码结合到一个笔记本里运行。
只需在每个单元格的开始,用Jupyter magics调用kernal的名称:
%% bash
%% HTML
%% python2
%% python3
%% ruby
%% perl
在[6]中:
{1..5}中i的%% bash
会
回显“ i is $ i”,
是
i是1
i是2
我是3
我是4
我是5
19-27
19.给Jupyter安装其他的内核
Jupyter的优良性能之一是可以运行不同语言的内核。下面以运行R内核为例说明:
简单的方法:通过Anaconda安装R内核
conda install -c r r-essentials
稍微麻烦的方法:手动安装R内核
如果你不是用Anaconda,过程会有点复杂,首先,你需要从CRAN安装R。
之后,启动R控制台,运行下面的语句:
install.packages(c('repr', 'IRdisplay', 'crayon', 'pbdZMQ', 'devtools'))
devtools::install_github('IRkernel/IRkernel')
IRkernel::installspec() # to register the kernel in the current R installation
20.在同一个notebook里运行R和Python
要这么做,最好的方法事安装rpy2(需要一个可以工作的R),用pip操作很简单:
pip install rpy2
然后,就可以同时使用两种语言了,甚至变量也可以在二者之间公用:
In [1]: %load_ext rpy2.ipython
In [2]: %R require(ggplot2)
Out[2]: array([1], dtype=int32)
In [3]: import pandas as pd
df = pd.DataFrame({
'Letter': ['a', 'a', 'a', 'b', 'b', 'b', 'c', 'c', 'c'],
'X': [4, 3, 5, 2, 1, 7, 7, 5, 9],
'Y': [0, 4, 3, 6, 7, 10, 11, 9, 13],
'Z': [1, 2, 3, 1, 2, 3, 1, 2, 3]
})
In [4]: %%R -i df
ggplot(data = df) + geom_point(aes(x = X, y= Y, color = Letter, size = Z))
21.用其他语言写函数
有时候numpy的速度有点慢,我想写一些更快的代码。
原则上,你可以在动态库里编译函数,用python来封装…
但是如果这个无聊的过程不用自己干,岂不更好?
你可以在cython或fortran里写函数,然后在python代码里直接调用。
首先,你要先安装:
!pip install cython fortran-magic
In [ ]: %load_ext Cython
In [ ]: %%cython
def myltiply_by_2(float x):
return 2.0 * x
In [ ]: myltiply_by_2(23.)
我个人比较喜欢用Fortran,它在写数值计算函数时十分方便。更多的细节在(http://arogozhnikov.github.io/2015/09/08/SpeedBenchmarks.html)。
In [ ]: %load_ext fortranmagic
In [ ]: %%fortran
subroutine compute_fortran(x, y, z)
real, intent(in) :: x(:), y(:)
real, intent(out) :: z(size(x, 1))
z = sin(x + y)
end subroutine compute_fortran
In [ ]: compute_fortran([1, 2, 3], [4, 5, 6])
还有一些别的跳转系统可以加速python 代码。更多的例子见
你可以在cython或fortran里写函数,然后在python代
22.支持多指针
Jupyter支持多个指针同步编辑,类似Sublime Text编辑器。按下Alt键并拖拽鼠标即可实现。
23.Jupyter外界拓展
Jupyter-contrib extensions是一些给予Jupyter更多更能的延伸程序,包括jupyter spell-checker和code-formatter之类.
下面的命令安装这些延伸程序,同时也安装一个菜单形式的配置器,可以从Jupyter的主屏幕浏览和激活延伸程序。
!pip install
!pip install jupyter_nbextensions_configurator
!jupyter contrib nbextension install --user
!jupyter nbextensions_configurator enable --user
24.从Jupyter notebook创建演示稿
Damian Avila的RISE(https://github.com/damianavila/RISE)允许你从已有的notebook创建一个powerpoint形式的演示稿。
你可以用conda来安装RISE:
conda install -c damianavila82 rise
或者用pip安装:
pip install RISE
然后运行下面的代码来安装和激活延伸程序:
jupyter-nbextension install rise --py --sys-prefix
jupyter-nbextension enable rise --py --sys-prefix
25.Jupyter输出系统
Notebook本身以HTML的形式显示,单元格输出也可以是HTML形式的,所以你可以输出任何东西:视频/音频/图像。
这个例子是浏览我所有的图片,并显示前五张图的缩略图。
In [12]: import os
from IPython.display import display, Image
names = [f for f in os.listdir('../images/ml_demonstrations/') if f.endswith('.png')]
for name in names[:5]:
display(Image('../images/ml_demonstrations/' + name, width=100))
我们也可以用bash命令创建一个相同的列表,因为magics和bash运行函数后返回的是python 变量:
In [10]: names = !ls ../images/ml_demonstrations/*.png
names[:5]
Out[10]: ['../images/ml_demonstrations/colah_embeddings.png',
'../images/ml_demonstrations/convnetjs.png',
'../images/ml_demonstrations/decision_tree.png',
'../images/ml_demonstrations/decision_tree_in_course.png',
'../images/ml_demonstrations/dream_mnist.png']
26.大数据分析
很多方案可以解决查询/处理大数据的问题:
ipyparallel(之前叫 ipython cluster) 是一个在python中进行简单的map-reduce运算的良好选择。我们在rep中使用它来并行训练很多机器学习模型。
pyspark
spark-sql magic %%sql
27.分享notebook
分享notebook最方便的方法是使用notebook文件(.ipynb),但是对那些不使用notebook的人,你还有这些选择:
通过File > Download as > HTML 菜单转换到html文件。
用gists或者github分享你的notebook文件。这两个都可以呈现notebook,示例见链接
如果你把自己的notebook文件上传到github的仓库,可以使用很便利的Mybinder服务,允许另一个人进行半个小时的Jupyter交互连接到你的仓库。
用jupyterhub建立你自己的系统,这样你在组织微型课堂或者工作坊,无暇顾及学生们的机器时就非常便捷了。
将你的notebook存储在像dropbox这样的网站上,然后把链接放在nbviewer,nbviewer可以呈现任意来源的notebook。
用菜单File > Download as > PDF 保存notebook为PDF文件。如果你选择本方法,我强烈建议你读一读Julius Schulz的文章
用Pelican从你的notebook创建一篇博客。
numpy的由来
1995年,Nuneric发布,没有进入python标准库
2001年,另一些开发者受到启发,开创了Scipy,是一个python科学计算库,提供了Matlab、Maple和Mathematica等功能
后来,Numarray作为Numeric的替代品问世了
2006年NumPy 1.0发布的时候全部完成。于是NumPy拥有了Numeric(数字)和Numarray(数组)的所有特性,并且还新增了一些功能。
如上,SciPy在处理数组和矩阵时会调用NumPy。
一、数组创建
数组是Numpy中最基本的数据对象,也是一种大容量数据容器。他的强大之处在于人们能够像操作标量那样操作数组。这样编出的代码不仅简单易于理解,而且基本告别了for语句,大大提高了运算速度。数组(Ndarray)可以是一维的,也可以是多维的
1. 创建简单数组
-
np.array
import numpy as np # 创建简单的列表 a = [1, 2, 3, 4] # 将列表转换为数组 b = np.array(a) numpy.array(object, dtype = None, copy = True, order = None, subok = False, ndmin = 0) object 数组或嵌套的数列 dtype 数组元素的数据类型,可选 copy 对象是否需要复制,可选 order 创建数组的样式,C为行方向,F为列方向,A为任意方向(默认) subok 默认返回一个与基类类型一致的数组 ndmin 指定生成数组的最小维度
-
np.asarray
numpy.asarray(a, dtype = None, order = None) a 任意形式的输入参数,可以是,列表, 列表的元组, 元组, 元组的元组, 元组的列表,多维数组 dtype 数据类型,可选 order 可选,有"C"和"F"两个选项,分别代表,行优先和列优先,在计算机内存中的存储元素的顺序。
-
np.linspace()
linspace():返回在间隔[开始,停止]上计算的num个均匀间隔的样本。 numpy.linspace(start, stop, num=50, endpoint=True, retstep=False, dtype=None) start:起始值 stop:结束值 num:生成样本数,默认为50 endpoint:如果为真,则停止是最后一个样本。否则,不包括在内。默认值为True。 retstep:如果为真,返回(样本,步骤),其中步长是样本之间的间距 → 输出为一个包含2个元素的元祖,第一个元素为array,第二个为步长实际值
-
数组元素个数: array.size
-
数组形状: array.shape
-
数组维度: array.ndim
-
数组元素类型: array.dtype
-
np.arange 从数值范围创建数组
np.arange(0,12,2).reshape(2,3) # 从0到12步长为2 # reshape 重塑外形 reshape里的两个参数的乘积必须与数组的元素个数相等
-
改变数组形状(要求前后元素个数匹配)
print("reshape函数的使用!") one_20 = np.ones([20]) print("-->1行20列<--") print (one_20) one_4_5 = one_20.reshape([4, 5]) print("-->4行5列<--") print (one_4_5)
2.特殊数组
-
浮点0数组创建
array_zero = np.zeros(10) array_zero = np.zeros([10, 10]) # 输入行数和列数 # 创建2维0数组时,必须以元组形式输入行数和列数
-
浮点1数组创建
array_one = np.ones([10, 10])
-
空数组创建
array_empty = np.empty([10, 10]) # 注意:空矩阵并不为空,认为空矩阵全为空值或者零值是不对的,空矩阵里面的元素 都是返回的垃圾值
-
单位数组创建
array_identity = np.identity(10) array_identity = np.eye(10) # 创建一个正方的N*N的单位矩阵,对角线值为1,其余为0
-
模仿其他数组的外形创建特殊数组
np.empty_like(data_ar1) np.ones_like(data_ar1) np.zeros_like(data_ar1)
3. 创建随机数组
np.random.rand(10, 10)
创建指定形状(示例为10行10列)的数组(范围在0至1之间)np.random.uniform(0, 100)
创建指定范围内的一个数np.random.randint(0, 100)
创建指定范围内的一个整数np.random.normal(1.75, 0.1, (2, 3))
给定均值/标准差/维度的正态分布
二、数组的数据类型
bool 用一个字节存储的布尔类型(True或False)
inti 由所在平台决定其大小的整数(一般为int32或int64)
int8 一个字节大小,-128 至 127
int16 整数,-32768 至 32767
int32 整数,-2 ** 31 至 2 ** 32 -1
int64 整数,-2 ** 63 至 2 ** 63 - 1
uint8 无符号整数,0 至 255
uint16 无符号整数,0 至 65535
uint32 无符号整数,0 至 2 ** 32 - 1
uint64 无符号整数,0 至 2 ** 64 - 1
float16 半精度浮点数:16位,正负号1位,指数5位,精度10位
float32 单精度浮点数:32位,正负号1位,指数8位,精度23位
float64或float 双精度浮点数:64位,正负号1位,指数11位,精度52位
complex64 复数,分别用两个32位浮点数表示实部和虚部
complex128或complex 复数,分别用两个64位浮点数表示实部和虚部
-
array.dtype
查看类型 -
array.astype(np.float64)
修改类型# a.astype():转换数组类型 # 注意:养成好习惯,数组类型用np.int32,而不是直接int32
三、切片和索引
ndarray对象的内容可以通过索引或切片来访问和修改,与 Python 中 list 的切片操作一样。
1. 一维数组
-
通过内置的 slice 函数,并设置 start, stop 及 step 参数进行,从原数组中切割出一个新数组。
import numpy as np a = np.arange(10) s = slice(2,7,2) # 从索引 2 开始到索引 7 停止,间隔为2 print (a[s]) [2 4 6] # 分别设置起始,终止和步长的参数为 2,7 和 2。
-
通过冒号分隔切片参数 start:stop:step 来进行切片操作:
import numpy as np a = np.arange(10) b = a[2:7:2] # 从索引 2 开始到索引 7 停止,间隔为 2 print(b) [2 4 6] 冒号 : 的解释:如果只放置一个参数,如 [2],将返回与该索引相对应的单个元素。如果为 [2:],表示从该索引开始以后的所有项都将被提取。如果使用了两个参数,如 [2:7],那么则提取两个索引(不包括停止索引)之间的项。
-
选取赋值
array=np.arange(10) a. 通过列表对选区进行赋值 array[1:5]=[-1,-2,-3,-1] Out: array([ 0, -1, -2, -3, -1, 5, 6, 7, 8, 9]) b. 通过单元素对选区进行赋值 array[-1:3:-1]=0 Out: array([0, 1, 2, 3, 0, 0, 0, 0, 0, 0]) c. 通过数组对选区进行赋值 array[2:6]=np.array([0,3,6,7]) Out: array([0, 1, 0, 3, 6, 7, 6, 7, 8, 9]) d. 通过元组对选区进行赋值 array[-6::-1]=(2,6,8,0,1) Out: array([1, 0, 8, 6, 2, 5, 6, 7, 8, 9])
-
切片
array=np.arange(2,10,2) transport_1=array[0:3] # 切片产生 transport_1[0:2]=100 # 对数组切片的赋值影响原数据
-
copy() 原数据可以被保护起来
arr=np.arange(0,30,4) arr Out: array([ 0, 4, 8, 12, 16, 20, 24, 28]) arr2=arr[2:].copy() arr2[-1:2:-1]=(-11,-22,-33) arr Out[78]: array([ 0, 4, 8, 12, 16, 20, 24, 28]) #上面的切片赋值没有改变原数据
2. 二维数组
import numpy as np
a = np.array([[1,2,3],[3,4,5],[4,5,6]])
print(a)
# 从某个索引处开始切割
print('从数组索引 a[1:] 处开始切割')
print(a[1:])
输出结果为:
[[1 2 3]
[3 4 5]
[4 5 6]]
从数组索引 a[1:] 处开始切割
[[3 4 5]
[4 5 6]]
import numpy as np
a = np.array([[1,2,3],[3,4,5],[4,5,6]])
print (a[...,1]) # 第2列元素
print (a[1,...]) # 第2行元素
print (a[...,1:]) # 第2列及剩下的所有元素
输出结果为:
[2 4 5]
[3 4 5]
[[2 3]
[4 5]
[5 6]]
以下实例获取数组中(0,0),(1,1)和(2,0)位置处的元素。
import numpy as np
x = np.array([[1, 2], [3, 4], [5, 6]])
y = x[[0,1,2], [0,1,0]]
print (y)
输出结果为:
[1 4 5]
以下实例获取了 4X3 数组中的四个角的元素。 行索引是 [0,0] 和 [3,3],而列索引是 [0,2] 和 [0,2]。
import numpy as np
x = np.array([[ 0, 1, 2],[ 3, 4, 5],[ 6, 7, 8],[ 9, 10, 11]])
print ('我们的数组是:' )
print (x)
print ('\n')
rows = np.array([[0,0],[3,3]])
cols = np.array([[0,2],[0,2]])
y = x[rows,cols]
print ('这个数组的四个角元素是:')
print (y)
输出结果为:
我们的数组是:
[[ 0 1 2]
[ 3 4 5]
[ 6 7 8]
[ 9 10 11]]
这个数组的四个角元素是:
[[ 0 2]
[ 9 11]]
3. 高维数组
array=np.random.randint(10,30,size=(2,3,4))
#随机数创建三维数组,random是产生随机数的库,randint是产生10与30之间的离 散平均分布随机数的函数,参数size确定了三维数组外形。(两个3×4的二维数组 组成一个三维数组)
Out: array([[[12, 26, 17, 16],
[17, 23, 22, 22],
[12, 23, 15, 17]],
[[22, 17, 11, 15],
[17, 23, 19, 25],
[14, 27, 12, 29]]])
art[1,:,1:]
Out: array([[17, 11, 15],
[23, 19, 25],
[27, 12, 29]])
art[1,1]
Out: array([17, 23, 19, 25])
art[0,2]
Out: array([12, 23, 15, 17])
art[0,:,2]
Out: array([17, 22, 15])
art[1,1:3,1:4]
Out: array([[23, 19, 25], [27, 12, 29]])
art2[1,1:,:4]
Out: array([[17, 23, 19, 25], [14, 27, 12, 29]])
art2[1,:3,3:]
Out: array([[15], [25], [29]])
art2[1,:3,3]
Out: array([15, 25, 29])
# 注意上面两个结果内容一样但性质不同,一个是二维数组,一个是一维数组。
4. 布尔值数组索引
我们可以通过一个布尔数组来索引目标数组。
布尔索引通过布尔运算(如:比较运算符)来获取符合指定条件的元素的数组。
以下实例获取大于 5 的元素:
import numpy as np
x = np.array([[ 0, 1, 2],[ 3, 4, 5],[ 6, 7, 8],[ 9, 10, 11]])
print ('我们的数组是:')
print (x)
# 现在我们会打印出大于 5 的元素
print ('大于 5 的元素是:')
print (x[x > 5])
输出结果为:
我们的数组是:
[[ 0 1 2]
[ 3 4 5]
[ 6 7 8]
[ 9 10 11]]
大于 5 的元素是:
[ 6 7 8 9 10 11]
以下实例使用了 ~(取反运算符)来过滤 NaN。
- np.isnan()
import numpy as np
a = np.array([np.nan, 1,2,np.nan,3,4,5])
print(np.isnan(a))
print (a[~np.isnan(a)])
输出结果为:
[ True False False True False False False]
[ 1. 2. 3. 4. 5.]
5. 花式索引
花式索引指的是利用整数数组进行索引。
花式索引根据索引数组的值作为目标数组的某个轴的下标来取值。对于使用一维整型数组作为索引,如果目标是一维数组,那么索引的结果就是对应位置的元素;如果目标是二维数组,那么就是对应下标的行。
花式索引跟切片不一样,它总是将数据复制到新数组中。
-
行索引排序
# 选取行排序 import numpy as np x=np.arange(15).reshape((5,3)) print(x) print (x[[3,2,4]]) #选取中括号内的行,并且按照3,2,4的顺序排列 输出结果为: [[ 0 1 2] [ 3 4 5] [ 6 7 8] [ 9 10 11] [12 13 14]] [[ 9 10 11] [ 6 7 8] [12 13 14]]
-
列索引排序
# 选取列排序 print (x[:,[2,0,1]]) 输出结果为: [[ 2 0 1] [ 5 3 4] [ 8 6 7] [11 9 10] [14 12 13]]
-
传入多个索引数组(要使用np.ix_)
import numpy as np x=np.arange(32).reshape((8,4)) print (x[np.ix_([1,5,7,2],[0,3,1,2])]) # print (x[[1,5,7,2]][:,[0,3,1,2]]) 效果一样 输出结果为: [[ 4 7 5 6] [20 23 21 22] [28 31 29 30] [ 8 11 9 10]]
-
精确查找
import numpy as np x=np.arange(15).reshape((5,3)) print(x) print (x[[3,2,4],[1,2,0]]) # 第一个中括号里的整数索引码与第二个中括号里的整数索引码一起构成了一系列索 引坐标,通过这些索引坐标可以实现精确查找。 输出结果为: [[ 0 1 2] [ 3 4 5] [ 6 7 8] [ 9 10 11] [12 13 14]] [10 8 12]
四、数组操作
1. 转置 (翻转数组)
函数 | 描述 |
---|---|
transpose |
对换数组的维度 |
ndarray.T |
和 self.transpose() 相同 |
rollaxis |
向后滚动指定的轴 |
swapaxes |
对换数组的两个轴 |
-
ndarray.T
import numpy as np ar1 = np.arange(10) ar2 = np.ones((5,2)) print(ar1,'\n',ar1.T) print(ar2,'\n',ar2.T) # .T方法:转置,例如原shape为(3,4)/(2,3,4),转置结果为(4,3)/(4,3,2) → 所以一维数组转置后结果不变 # 高维数组的全转置通过transpose(2,1,0)来实现,它等同于'.T':
-
numpy.transpose
numpy.transpose(arr, axes) arr:要操作的数组 axes:整数列表,对应维度,通常所有维度都会对换。 没有转置前的高维数组轴编号顺序总是为:(0,1,2...)。通过transpose函数可以 把未转置的数组轴编号布局(0,1,2...)转换到transpose参数指定的轴编号布局。
转置过程: 转置前轴编号布局 (0,1,2) (1,0,2) 转置后轴编号布局 从轴编号布局变化看出:0轴和1轴位置互换,那么随之导致数组外形和元素布局的变 化。 转置前数组外形(2,2,4) 转置后数组外形 (2,2,4)。 处在外形元组0位置的2和处在1位置2也必须按照轴编号布局的变化互换位置。然后他 们恰恰都是2,因此矩阵外形不发生变化。 转置前元素‘4’的索引(0,1,0) 转置后元素‘4’的索引(1,0,0) 处在索引元组0位置的0和处在1位置1也必须按照轴编号布局的变化互换位置变成 (1,0,0),(1,0,0)恰恰是元素‘4’在转置后矩阵中的索引
2. 修改数组形状
函数 | 描述 |
---|---|
reshape |
不改变数据的条件下修改形状 |
flat |
数组元素迭代器 |
flatten |
返回一份数组拷贝,对拷贝所做的修改不会影响原始数组 |
ravel |
返回展开数组 |
ar1.reshape(2,5)
# 方法1:直接将已有数组改变形状
np.zeros((4,6)).reshape(3,8)
# 方法2:生成数组后直接改变形状
np.reshape(np.arange(12),(3,4))
# 方法3:参数内添加数组,目标形状
-
numpy.reshape
numpy.reshape 函数可以在不改变数据的条件下修改形状,格式如下: numpy.reshape(arr, newshape, order='C') arr:要修改形状的数组 newshape:整数或者整数数组,新的形状应当兼容原有形状 order:'C' -- 按行,'F' -- 按列,'A' -- 原顺序,'k' -- 元素在内存中的出现顺序。 # 为数组提供新形状,而不更改其数据,所以元素数量需要一致!!
-
numpy.resize
np.resize(np.arange(5),(3,4)) numpy.resize(a, new_shape) # 返回具有指定形状的新数组,如有必要可重复填充所需数量的元素。
-
numpy.ndarray.flatten
返回一份数组拷贝,对拷贝所做的修改不会影响原始数组 ndarray.flatten(order='C') order:'C' -- 按行,'F' -- 按列,'A' -- 原顺序,'K' -- 元素在内存中的出现顺序。
-
array.ravel()
将多维数组降位一维,返回的是视图,会影响(reflects)原始矩阵。
-
ndarray.copy(): copy方法生成数组及其数据的完整拷贝
3. 连接数组
函数 | 描述 |
---|---|
concatenate |
连接沿现有轴的数组序列 |
stack |
沿着新的轴加入一系列数组。 |
hstack |
水平堆叠序列中的数组(列方向) |
vstack |
竖直堆叠序列中的数组(行方向) |
-
numpy.stack
numpy.stack 函数用于沿新轴连接数组序列 numpy.stack(arrays, axis) arrays相同形状的数组序列 axis:返回数组中的轴,输入数组沿着它来堆叠 numpy.stack(arrays, axis=0):沿着新轴连接数组的序列,形状必须一样!
-
numpy.hstack
numpy.hstack 是 numpy.stack 函数的变体,它通过水平堆叠来生成数组。 numpy.hstack(tup):水平(按列顺序)堆叠数组
-
numpy.vstack
numpy.vstack 是 numpy.stack 函数的变体,它通过垂直堆叠来生成数组。 numpy.vstack(tup):垂直(按行顺序)堆叠数组
-
numpy.concatenate
numpy.concatenate((a1,a2,...),axis) 函数用于沿指定轴连接相同形状的两个或多个数组 a1, a2, ...:相同类型的数组 axis:沿着它连接数组的轴,默认为 0
-
numpy.column_stack
numpy.column_stack((a1,a2))
-
numpy.row_stack
numpy.row_stack((a1,a2))
-
column_stack 与 hstack 区别
np.column_stack()中的axis类似于np.hstack(tuple)。 关于np.hstack中的理解:Stack arrays in sequence horizontally (column wise) np.hstack((a,b)),如果a、b是list,则在列上叠加;如果a、b是矩阵array,则在行相同时扩展列,行不变。 >>> a = np.array((1,2,3)) >>> b = np.array((2,3,4)) >>> np.hstack((a,b)) array([1, 2, 3, 2, 3, 4]) >>> a = np.array([[1],[2],[3]]) >>> b = np.array([[2],[3],[4]]) >>> np.hstack((a,b)) array([[1, 2], [2, 3], [3, 4]]) # 其中np.column_stack()与np.hstack()区别: 对于1d的list,会行不变列扩展;对于2d的array,如3*1的array或者list,一样是行不变列扩展。 # 一 a=[1, 2, 3] b=[11, 22, 33] np.column_stack((a,b)) Out[21]: array([[ 1, 11], [ 2, 22], [ 3, 33]]) # 二 np.column_stack(([[1],[2],[3]],[[11],[12],[13]])) Out[22]: array([[ 1, 11], [ 2, 12], [ 3, 13]]) # 三 a_array = np.array([[1],[2],[3]]) b_array = np.array([[2],[3],[4]]) np.column_stack((a_array, b_array)) Out[26]: array([[1, 2], [2, 3], [3, 4]])
4. 分割数组
函数 | 数组及操作 |
---|---|
split |
将一个数组分割为多个子数组 |
hsplit |
将一个数组水平分割为多个子数组(按列) |
vsplit |
将一个数组垂直分割为多个子数组(按行) |
-
numpy.split
沿特定的轴将数组分割为子数组 numpy.split(ary, indices_or_sections, axis) ary:被分割的数组 indices_or_sections:果是一个整数,就用该数平均切分,如果是一个数组,为沿轴切分的位置(左开右闭) axis:沿着哪个维度进行切向,默认为0,横向切分。为1时,纵向切分
-
numpy.hsplit
用于水平分割数组,通过指定要返回的相同形状的数组数量来拆分原数组。
-
numpy.vsplit
沿着垂直轴分割,其分割方式与hsplit用法相同。
五、数组运算
1. 数组简单运算
# 数组简单运算
ar = np.arange(6).reshape(2,3)
print(ar + 10) # 加法
print(ar * 2) # 乘法
print(1 / (ar+1)) # 除法
print(ar ** 0.5) # 幂
# 与标量的运算
print(ar.mean()) # 求平均值
print(ar.max()) # 求最大值
print(ar.min()) # 求最小值
print(ar.std()) # 求标准差
print(ar.var()) # 求方差
print(ar.sum(), np.sum(ar,axis = 0)) # 求和,np.sum() → axis为0,按列求和;axis为1,按行求和
print(np.sort(np.array([1,4,3,2,5,6]))) # 排序
2. 一元函数
ndarray中的数据执行元素级运算的函数
函数 | 说明 |
---|---|
np.abs(x) np.fabs(x) | 计算数组各元素的绝对值 |
np.sqrt(x) | 计算数组各元素的平方根 |
np.square(x) | 计算数组各元素的平方 |
np.log(x) np.log10(x) np.log2(x) | 计算数组各元素的自然对数、10底对数和2底对数 |
np.ceil(x) np.floor(x) | 计算数组各元素的ceiling向上取整值 或 floor向下取整值 |
np.rint(x) | 计算数组各元素的四舍五入值 |
np.modf(x) | 将数组各元素的小数和整数部分以两个独立数组形式返回 |
np.cos(x) np.cosh(x) np.sin(x) np.sinh(x) np.tan(x) np.tanh(x) | 计算数组各元素的普通型和双曲型三角函数 |
np.exp(x) | 计算数组各元素的指数值 |
np.sign(x) | 计算数组各元素的符号值,1(+), 0, ‐1(‐) |
3. 二元函数
函数 | 说明 |
---|---|
+ ‐ * / ** | 两个数组各元素进行对应运算 |
np.maximum(x,y) np.fmax() np.minimum(x,y) np.fmin() | 元素级的最大值/最小值计算 |
np.mod(x,y) | 元素级的模运算 |
np.add(a,b) | 元素级的加法运算 |
np.subtract(a,b) | 元素级的减法运算 |
np.multiply(a,b) | 元素级的乘法运算 |
np.divide(a,b) | 元素级的除法运算 |
np.copysign(x,y) | 将数组y中各元素值的符号赋值给数组x对应元素 |
> < >= <= == != | 算术比较,产生布尔型数组 |
np.power(a,b) | a是底,b是幂 |
六、条件刷选函数
-
numpy.sort()
函数返回输入数组的排序副本 numpy.sort(a, axis, kind, order) a: 要排序的数组 axis: 沿着它排序数组的轴,如果没有数组会被展开,沿着最后的轴排序, axis=0 按列排序,axis=1 按行排序 kind: 默认为'quicksort'(快速排序) order: 如果数组包含字段,则是要排序的字段
-
numpy.argsort() 返回的是数组值从小到大的索引值。
-
numpy.argmax() 和 numpy.argmin()
numpy.argmax(array,0/1) 和 numpy.argmin()函数分别沿给定轴返回最大和最小元素的索引。
-
numpy.nonzero() 返回输入数组中非零元素的索引。
-
np.where()
函数返回输入数组中满足给定条件的元素的索引。np.where(condition, [x, y]) condition:bool-array-like x,y:array-like 如果满足条件,返回x,否者y。 如果仅仅有条件,则返回true值所对应的索引
七、统计函数
-
array.sum() 求和
array.sum()/np.sum(array) 整个数组从头加到尾 array.sum(0)/np.sum(array,0) 对每列求和 array.sum(1)/np.sum(array,1) 对每行求和
-
array.mean() 求平均值
array.mean()/np.mean(array) 从头到尾求均值 array.mean(0)/np.mean(array,0) 按列求均值 array.mean(1)/np.mean(array,1) 按行求均值
-
array.min() /array.min() 求最小值/最大值
array.min()/np.min(array) 从头到尾求均值 array.min(0)/np.min(array,0) 按列求均值 array.min(1)/np.min(array,1) 按行求均值
-
array.cumsum() 所有元素的累积和
array.cumsum() 在整个数组中从头到尾依次累加形成一维数组 array.cumsum(0) 按列累加 array.cumsum(1) 按行累加
-
array.cumprod()(所有元素的累积积)
-
方差
统计中的方差(样本方差)是每个样本值与全体样本值的平均数之差的平方值的平均数,即 mean((x - x.mean())** 2)。
换句话说,标准差是方差的平方根。
-
标准差
标准差是一组数据平均值分散程度的一种度量。
标准差是方差的算术平方根。
标准差公式如下:
std = sqrt(mean((x - x.mean())**2))
八、数组排序,去重
1. 排序
sort用作函数(np.sort)是一次性排序,用做方法(.sort)是永久性排序。
-
numpy.sort() 用作函数
函数返回输入数组的排序副本 numpy.sort(a, axis, kind, order) a: 要排序的数组 axis: 沿着它排序数组的轴,如果没有数组会被展开,沿着最后的轴排序, axis=0 按列排序,axis=1 按行排序 kind: 默认为'quicksort'(快速排序) order: 如果数组包含字段,则是要排序的字段
-
array.sort()
array.sort(0) # 对每一列进行排序 array.sort(1) # 对每一行进行排序
2. 去重
-
np.unique()
np.unique(array,axis=0) # 删除重复行并对第一列进行排序 np.unique(array,axis=1)# 删除重复列并对第一行进行排序
九、bool数组方法
-
bool_ar.sum()
#通过sum()函数可以统计bool_ar中的True的数量,这就意味着我们可以统计出符合条件的数据量 bool_ar.sum(axis=0) # 按列 bool_ar.sum(axis=1) # 按行
-
bool_ar.all() 检验数组是不是全是true
-
bool_ar.any() 检验数组是不是有true
十、数组集合运算
函数 | 说明 | 例子 | 结果 |
---|---|---|---|
unique(x) | 计算x中唯一元素,并返回有序的结果 | np.unique(s0) | [1 2 3 4 5] |
intersect1d(x,y) | 交集,并返回有序结果 | np.intersect1d(s1,s2) | [ 0 6 12 18 24] |
union1d(x,y) | 并集,并返回有序结果 | np.union1d(s1,s2) | [ 0 2 3 4 6 8 9 10 12 14 15 16 18 20 21 22 24 26 27 28] |
setdiff1d(x,y) | 集合差,即元素在x中且不再y中 | np.setdiff1d(s1,s2) | [ 2 4 8 10 14 16 20 22 26 28] |
setxor1d(x,y) | 集合对称差,只存在x和y中的元素集合 | np.setxor1d(s1,s2) | [ 2 3 4 8 9 10 14 15 16 20 21 22 26 27 28] |
in1d(x,y) | 得到一个”x的元素是否包含于y”的布尔行数组 | np.in1d(s2,s1) | [ True False True False True False True False True False] |
-
np.in1d : np.in1d(a,b) a是否包含于b
其作用在于在序列B中寻找与序列A相同的值,并返回一逻辑值(True,False)或逻辑值构成的向量。 np.in1d(ar1, ar2, assume_unique=False, invert=False)
-
np.intersect1d : 交集,并返回有序结果
>>> np.intersect1d([1, 3, 4, 3], [3, 1, 2, 1]) array([1, 3])
-
np.union1d: 并集,并返回有序结果
-
np.setdiff1d: 集合的差
-
np.setxor1d: 对称差集
十一、数据的输入输出
1. 读取
① .npy 文件
# 读取数组数据 .npy文件
ar_load =np.load('arraydata.npy')
print(ar_load)
# 也可以直接 np.load('D:\Desktop\arraydata.npy')
② .txt/.csv 文件
ar_loadtxt = np.loadtxt('array.txt', delimiter=',')
print(ar_loadtxt)
# 也可以直接 np.loadtxt('D:\Desktop\arraydata.txt')
③ .xls 文件
import numpy as np
import xlrd
name=r'C:\Users\dongfeng\Desktop\yong.xls'
test1=xlrd.open_workbook(name) # 打开工作薄
table = test1.sheet_by_name(u'Sheet1') # 打开待读取表格并赋给变量
table daten1=[]
nrows = table.nrows # 计算表格table行数。表格行索引是从0开始编号。假设此表格有5行, 即nrows=5,则行编号分别是0,1,2,3,4
for j in range(1,nrows,1):
daten1.append(list(table.row_values(j)))
#上面的方法是从excel表格读取数据的繁琐方法,后面讲到pandas时,会有更为简单的 方法。
array_ur=np.array(daten1)
2. 存储
① .npy 文件
# 存储数组数据 .npy文件
import os
os.chdir('D:\Desktop\')
ar = np.random.rand(5,5)
print(ar)
np.save('arraydata.npy', ar)
# 也可以直接 np.save('D:\Desktop\arraydata.npy', ar)
② .txt 文件
ar = np.random.rand(5,5)
np.savetxt('array.txt',ar, delimiter=',')
# np.savetxt(fname, X, fmt='%.18e', delimiter=' ', newline='\n', header='', footer='', comments='# '):存储为文本txt文件
十二、项目:数据清洗
def get_repeated_label(array_1dim):
label_1dim=[]
for k in range(len(array_1dim)-1):
for i in range(k+1,len(array_1dim),1):
if array_1dim[k]==array_1dim[i]:
label_1dim.append(i)
return np.unique(label_1dim)
#此函数可以返回一维数组中的重复项索引
def invalid_value_cleaning (array_variable):
for i in range(np.shape(array_variable)[0]):
for j in range(np.shape(array_variable)[1]):#通过i,j循环遍查整个二维数组
if type(array_variable[i,j])==float or type(array_variable[i,j])==int:#对二维数组中的每一个元素的类型进行判断,如果是整数或者小数,我们把其忽略,如果不是,则替换成0
pass
else:
array_variable[i,j]=0
array_variable[np.isnan(array_variable.astype(np.float64))]=0#通过isnan函数数组转换为bool数组,然后放到array_variable的索引位选住所有空值(nan)使其替换为0
return array_variable
# 第二个函数实现无效值替换,凡是不是整数或者小数的数组元素均被替换为0
def fillup_mean_value(array_parameter):
for index_j in range(np.shape(array_parameter)[1]):#遍查二维数组的每一列
array_columns_nr=list(np.where(array_parameter==0)[1])#把每一列中的0元素的列索引做成列表传给变量array_columns_nr
if index_j in array_columns_nr:#在上面生成的列表中循环,即在0元素所对应的列索引组成的列表中循环
appearance_sum=array_columns_nr.count(index_j)#对列表中与index_j相等的列索引进行计数,等价于确定每列中0的个数
if appearance_sum>0:#如果一列中有0值
mean_1=(array_parameter[:,index_j]).sum()/(np.shape(array_parameter)[0]-appearance_sum)#计算算数平均值,注意分母要减去0元素的个数,也就是说0元素不计算在呢,因为0元素是替换无效值而得。
bollmatrix_1=array_parameter[:,index_j]==0#通过布尔数组确定0元素的位置
array_parameter[bollmatrix_1,index_j]=mean_1#选中index_j列中所有0元素,替换为平均值
return array_parameter
# 第三个函数实现用平均值替换0值,实际是平均值替换无效值,即平均值补值法。
def delete_rows(list_variable,array_variable):
array_medium=np.delete(array_variable,list_variable,0)
return array_medium
# 第四个函数可以删除重复行
参考文献
关于 Qgrid 的全部功能
https://github.com/quantopian/qgrid。
以上就是强化 Jupyter Notebook 功能的 4 种方法(翻墙)
https://towardsdatascience.com/4-awesome-tips-for-enhancing-jupyter-notebooks-4d8905f926c5