89

1个等式!3行代码!78倍!如何加速机器学习算法?

 4 years ago
source link: https://www.tuicool.com/articles/emUVFbr
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.

Vj6R3qb.jpg!web

标星★公众号      爱你们    

作者:Ioannis Gatopoulos

编译:1+1=6

近期原创文章:

♥  5种机器学习算法在预测股价的应用(代码+数据)

♥  Two Sigma用新闻来预测股价走势,带你吊打Kaggle

 2万字干货: 利用深度学习最新前沿预测股价走势

♥  机器学习在量化金融领域的误用!

♥  基于RNN和LSTM的股市预测方法

♥  如何鉴别那些用深度学习预测股价的花哨模型?

♥  优化强化学习Q-learning算法进行股市

♥  WorldQuant 101 Alpha、国泰君安 191 Alpha

♥  基于回声状态网络预测股票价格(附代码)

♥  计量经济学应用投资失败的7个原因

♥  配对交易千千万,强化学习最NB!(文档+代码)

♥  关于高盛在Github开源背后的真相!

♥  新一代量化带货王诞生!Oh My God!

♥  独家!关于定量/交易求职分享(附真实试题)

♥  Quant们的身份危机!

♥  AQR最新研究 | 机器能“学习”金融吗

众所周知,Python的for循环本质上要比C慢很多。 而且深度学习和机器学习算法严重依赖通过for循环执行的矩阵运算。

这就是为什么像numpy等这样包诞生,它们在numpy数组上提供向量化的操作。这意味着它将通常在Python中完成的for循环推进到C的级别。

我们希望将最大期望算法(Expectation-Maximization algorithm, EM)用于无监督学习(例如,识别MNIST数据集中的手写数字),并且我们的数据是二进制的(例如,二进制图像)。一种常见的方法是将数据建模为伯努利混合模型;一个人伯努利分布的加权和,如果每个分布有自己的标量权重π和自己的平均向量μ,并表示一组数据(例如,如果我们的数据是数字2、3&4的图形,我们使用3伯努利模型,一个伯努利将是数字2,另一个是4,等等)。总的来说,前者是一个向量,后者是一个矩阵。

bErimeQ.png!web

Bernoulli mixture model

QZRZZvN.png!web

Distribution of one observation x given the cluster k 

在E-step中,我们特别感兴趣的是隐变量后验的期望值,也就是所谓的responsibilities

ANFjiiE.jpg!web

E-step of EM algorithm

γ实际返回的期望值观察n属于集群k。

γ是一个NxK矩阵;对于每个观测,我们分配的一个概率属于每个集群。最大值是我们指定的值。

因为: 向量化过程中最重要的事情是要理解变量的维数。

  • X : NxD matrix

  • π : 1xK vector

  • μ : KxD matrix

  • γ : NxK matrix

Pipeline

我们将创建一个E_step函数来计算上面的表达式并用下面的代码进行测试:

YZFBZ3U.jpg!web

第一次尝试

在第一次尝试中,我们将使用 for 循环编写所有内容;在向量/矩阵操作中,只使用标量。

通过观察这些方程,我们可以看到有3个循环,每个例子 D 有一个循环,每个集群 K 有一个循环,每个对象 D 有一个循环,我们将按这个顺序循环。所以我们要每次用一个元素填充矩阵γ。

VBR3euj.jpg!web

下图是结果:

eInau2u.jpg!web

第二次尝试

最好从内部循环开始,然后逐步进入外部循环。这正是我们要做的!

我们想去掉for loop D。因此,每个依赖于 D 的term应该变成一个向量。在for loop中,我们有两个变量;μ和x。因此 x 和 μ → 向量。问题是,它是 μ**x。

有一个函数,它把一个幂运算变成了乘法运算。没错,就是对数!因此, 让我们使用对数来表示我们的表达式 ,然后对结果取指数。

关于对数概率的操作是首选的,因为它们提供了数值稳定性!

即使在我们的例子中它没有任何影响,每次你使用对数的时候,在表达式中使用一个常量 epsilon 来表示稳定性(不趋于0,是-inf)。

因此,我们将不得不对元素进行矢量乘法,easy!

jAvUner.jpg!web

结果是:

imUJbqY.jpg!web

第三次尝试

一次一个loop:K turn

在向量化过程中,有如下操作:

标量→向量→矩阵

当我们用numpy数组替换越来越多的循环时,越来越多的代码将在C上运行。

我们使用之前的实现,我们想要删除K for loop。因此,每一个依赖于K的标量都会变成一个向量,每一个向量都会变成一个矩阵。这意味着X和μ将保持不变,π变成矩阵,γ变成向量。

ZNF7zyV.jpg!web

结果:

EJVZVf7.jpg!web

ErURRrA.jpg!web

n=1000的时候,我们只花了一半的时间!

第四次尝试

还有一个循环。我们可以有一个loop-python-free吗?come on!

由于我们要将 矩阵*向量 运算转换成 矩阵@矩阵 运算,我们需要取前者的传输矩阵(@是正则的矩阵乘法)。记住,现在我们的输出必须是整个γ矩阵。

UFvIfyB.png!web

一个循环也没有! 代码看起来很优雅,只有三行!

qYBjm2B.jpg!web

YbQNriR.jpg!web

对于n=1000,我们的运行时长 从11.688下降到0.012!

那么,当你想向量化一个表达式时,你需要做什么呢?

1、 了解矩阵的大小。

2、 一支笔一张纸: 写下公式,从一个求和到另一个求和,把它变成一个等价的矩阵运算。

3、 数学是你的朋友: 总是对任何表达式必须返回的维数进行推理;观察相邻的求和操作,因为它们具有相同的维度。

4、一个循环一个循环,一步步: 标量→向量→矩阵。

5、 取对数 ,确保引入标准化常数。

6、为你的方法编写向量版的代码。

来自: https://twitter.com/TDataScience

—End—

量化投资与机器学习微信公众号,是业内垂直于 Quant MFE CST、AI 等专业的 流量化自媒体 。公众号拥有来自 公募、私募、券商、银行、海外 等众多圈内 18W+ 关注者。每日发布行业前沿研究成果和最新量化资讯。

你点的每个“在看”,都是对我们最大的鼓励


About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK