大规模分布式机器学习之参数服务器

概述

参数服务器是分布式机器学习框架中用来作为参数同步的框架,现在很多大规模的分布式机器学习都采用参数服务器架构用来进行参数的同步以提升大规模的模型的速度和效率。由于我们现在正处于一个大数据的时代,如何结合海量数据和超大规模的模型进行应用?比如现在以小视频和短视频(时序特征+内容特征+用户等多维度特征巨大)为主的推荐、广告、视频算法、搜索等都要采用大规模分布式机器学习系统,比如短视频为主的多模态学习更是需要大规模的分布式机器学习来快速满足产品场景化需求、画像更新、视频流算法、智能化内容创作、聚类、灰度算法及时调整、老用户的运营模型以及如何将流量转为价值过程中的模型,大规模分布式机器学习系统都充当了底层基石。分布式学习系统包括两大模块:模型和分布式系统。其中模型需要解决训练和正确率的问题,分布式系统需要考虑并行、网络、慢机、故障处理、调度、数据一致性等问题。最近在看mxnet的源码,我们一起学习一下参数服务的架构和设计,更为详细的可以参考mxnet官网。

现有系统的不足

MapReduce:迭代式计算低效,节点之间通信效率不高

MPI:无法支撑大数据,任意节点挂掉,任务就失败,多节点共享内存的方式以及测试比较复杂和调试困难

Graph:用图来做抽象,类似深度学习无法高效求解,只能同步,不支持异步

Spark:通用框架,高维度和稀疏数据支持不够,Spark的并行梯度下降方法是同步阻断式的,且模型参数需通过全局广播的形式发送到各节点

2014年分布式可扩展的Parameter Server被沐神(李沐)提出,几乎完美的解决了机器模型的分布式训练问题,现在我们常说的Parameter Server属于第三代参数服务器。其特点如下:

  • Efficient Communication:异步通信模型,最优化机器学习任务来减少网络负担。

  • Flexible Consistency Models:允许算法设计者去平衡算法收敛率与系统效率。

  • Elastic Scalability:在无需重启运行中的框架下便可添加新节点。

  • Fault Tolerance and Durability

  • Ease of Use

综合考虑性价比高的选择是参数服务器(Parameter Sever),其架构如下图所示:

参数服务器

其算法如下:

参数服务器算法

机器学习十大算法入门系列之感知机

概述

感知机(perceptron)是个二类分类的线性分类模型,该算法对应于特征空间将实例划分为正负两类的分离超平面,属于判别模型。判别模型是一种对未观测数据y与已观测数据x之间关系进行建模的方法,直接对条件概率p(y|x;θ)建模。直接假设判别函数的参数形式是已知的 ,然后基于训练样本,使用某种学习算法,来学习判别函数的参数值,被称为判别式方法,感知机所得到的是一个线性判别函数。而一般来说,寻找线性判别函数的问题,会被形式化为极小化准则函数的问题,以分类为目的的准则函数可以是样本的风险函数,或者是训练误差。 从机器学习的角度来讲,感知机属于监督学习(supervised learning),它是一个单层的二分类器。感知机算法非常重要,它是神经网络和SVM的基础。感知机算法如下图所示:

感知机算法

平台化SaaS实践之Docker Stack应用

概述

SaaS (软件即服务)是一种许可和交付模式,其中软件由提供商集中托管和管理,并通过订阅的方式提供给用户,用户也可以按需或者即用即付方式进行购买。所有基础结构、中间件、应用软件和应用数据都位于服务提供商的数据中心内。提供商负责管理硬件和软件,并根据适当的服务协议确保应用和数据的可用性和安全性。现在很多传统软件向SaaS“转变”时,更多的是向平台化SaaS软件靠拢,借助此模式来交付的产品优势很多,比如:

  • 提供灵活的方式满足客户需求
  • 提高运营效率,使其专注于产品
  • 打破地域的限制,全球覆盖面,从任何位置访问应用数据
  • 按需交付,多维度
  • 自传播
  • 隔离性、安全性、可定制性度高

平台+软件=平台化SaaS=支撑层+应用层

TensorFlow Serving and Flask Delpoy Models

概述

当我们要去部署和测试深度学习models时,我们经常需要一个比较便利和接口方便的web server,这样我们只需要专注在Model本身即可,通过web server一方面不仅可以进行调试和测试, 另外一方面还可以将自己的成果输出给第三方和用户去体验深度学习带来的便利。大家经常使用的方式有以下两种(以TensorFlow为主):

  • TensorFlow Serving
  • TensorFlow Models + web server

如果你的模型很多,那么就需要结合云计算的AI工具箱进而支持大规模的深度学习线上、线下训练、预测以及发布等等,还会结合yarn和k8s进行节点、服务调度,微服务化的方式支持业务线。

C++ Development In Visual Studio Code

由于我工作环境是Linux和Mac,个人的工作目录和开发环境一直来回切换,之前一直使用emacs,emacs非常强大和可定制化。最近看到vscode的社区不断壮大,在好基友的推荐下,试用vscode,发现非常不错。于是记录和分享到博客中。今天主要给大家讲解的vscode配置c/c++ ide开发环境,当然官网支持很多种可定制化的配置。

开发环境搭建

我们首先安装vscode,官网是:vscode。我们下面来安装支持c/c++开发环境的安装包。 * cpptools * cmake * C/C++ Clang

我们在工作目录依次安装如下,c_cpp_properties.json(指定c/c++包和平台相关的配置文件),launch.json(debug 调试),tasks.json(你的编译等命令)

机器学习性能度量

我们在进行机器学习时需要衡量机器学习的优劣和本身模型的准确程度,比如简单的衡量数据的准确率和错误率,但是我们更关心的是模型的泛化能力的指标,即基于模型的所选的item相关性以及模型分类指标的好坏。

机器学习度量

  • error rate(错误率):把分类错误的样本数占样本总数的比例。$$E=a/m$$
  • accuracy(精确度):分类正确的样本数占样本总数的比例。$$acc=1-E$$
  • training error(训练误差):学习器在训练集上的误差。
  • generalization error(泛华误差):在新样本上的误差。

在机器学习中由很多机器学习算法,那么如何选择这些算法和模型,如何评估这些算法和模型,评估模型的算法和准确率的方式很多,我们依次来介绍一下几个常用的指标。TP、TN、FP、FN、Acc、Recall、F1、ROC和ROI

各种机器学习衡量指标

Accuracy、Precision、Recall和F1-Score

混淆矩阵是按照预测分类和实际分类的类别对比,如下图所示: 混淆矩阵 如上表所示,行表示预测的label值,列表示真实label值。TP,FP,FN,TN分别表示如下意思: * TP(true positive):表示样本的真实类别为正,最后预测得到的结果也为正 * FP(false positive):表示样本的真实类别为负,最后预测得到的结果却为正 * FN(false negative):表示样本的真实类别为正,最后预测得到的结果却为负 * TN(true negative):表示样本的真实类别为负,最后预测得到的结果也为负

$$ Accuracy = \frac{TP+TN}{TP+FP+TN+FN} $$ $$ Precision = \frac{TP}{TP+FP} $$ $$ Recall = \frac{TP}{TP+FN} $$ $$ SP = \frac{TN}{TN + FP}
$$

  • Accuracy:表示预测结果的精确度,预测正确的样本数除以总样本数。
  • Precision,准确率,表示预测结果中,预测为正样本的样本中,正确预测为正样本的概率;
  • Recall,召回率,表示在原始样本的正样本中,最后被正确预测为正样本的概率;
  • Specificity,常常称作特异性,它研究的样本集是原始样本中的负样本,表示的是在这些负样本中最后被正确预测为负样本的概率。

在实际当中,我们往往希望得到的precision和recall都比较高,比如当FN和FP等于0的时候,他们的值都等于1。但是,它们往往在某种情况下是互斥的。例如,有50个正样本,50个负样本,结果全部预测为正样本,那么TP=50,FP=50,TN=0,FN=0,按照上面的公式计算,可以得到正样本的recall却为1,precision却为0.5.所以需要一种折衷的方式,因此就有了F1-score。

$$ F1-score = \frac{2\times recall \times precision}{ recall + precision} $$

F1-score表示的是precision和recall的调和平均评估指标. 另外还有一个指标,即MCC,该指标对于不均衡数据集的评估非常有效,公式如下:

$$ MCC=\frac{(TP \times TN)-(FP \times FN)}{\sqrt{(TP+FP)\times(TP+FN)\times(TN+FP)\times(TN+FN)}} $$

结构化的机器学习流程

机器学习可以通过结构化的流程来梳理:1.定义问题和需求分析->2.数据探索->3.数据准备->4.评估算法->5.优化模型->6.部署。 * 导入类库 * 导入数据集 * 数据统计分析 * 数据可视化 * 数据清洗 * 特征选择 * 数据转换 * 分离数据集 * 定义模型评估标准 * 算法审查 * 算法比较 * 算法调参 * 集成算法 * 预测评估数据集 * 利用数据生成模型 * 序列化模型

数据理解

数据的理解主要在于分析数据维度、数据类型属性、数据分布以及相关性等。数据属性的相关性是指数据的两个属性的互相影响。

数据统计分析

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
# 数据导入与数据维度探索
from numpy import loadtxt
with open(filename,'rt') as rawdata:
    data = loadtxt(rawdata,delimiter=',')
    print(data.shape)
#数据属性和描述性统计
print(data.dtype)
print(data.describe())
#数据根据类别分类
print(data.group("class").size())
#数据属性相关性(皮尔逊相关系数,1完全正相关,-1完全负相关,0不相关)
print(data.corr(method="pearson"))
#数据分布分析,skew代表高斯分布的偏离程度,数据接近于0表示数据偏差非常小
print(data.skew())

熵的理解

熵在信息论中代表随机变量不确定度的度量。一个离散型随机变量X的熵H(X)定义为: $$ H(X)=- \sum_{x \in X} p(x) \cdot logp(x) $$ 明确定义的科学名词且与内容无关,而且不随信息的具体表达式的变化而变化。是独立于形式,反映了信息表达式中统计方面的性质。是统计学上的抽象概念。信息熵的一种解释是,它表示的是最短的平均编码长度。同样的,不确定性越大,熵就越大。信息熵的单位是比特(bit)。我们举两个简单的例子: 第一个例子: 32支球队,在无任何先验信息的前提下,用二分法猜冠军队伍,最多猜5次,即: $$ log\frac{1}{32}=5log\frac{1}{32}=5bit $$ 第二个例子:赌马比赛里,有4匹马A,B,C,D,获胜概率分别为 $$ \frac{1}{2},\frac{1}{4},\frac{1}{8},\frac{1}{8} $$

  • 如果 X=A ,那么需要问1次(问题1:是不是A?),概率为 $$ \frac{1}{2} $$
  • 如果 X=B ,那么需要问2次(问题1:是不是A?问题2:是不是B?),概率为 $$ \frac{1}{4}$$
  • 如果 X=C ,那么需要问3次(问题1,问题2,问题3),概率为
    $$ \frac{1}{8}$$
  • 如果 X=D ,那么同样需要问3次(问题1,问题2,问题3),概率为 $$ \frac{1}{8}$$

通过熵的定义得到

$$ H(x)=-\sum_{x \in {A,B,C,D}}p(x)\cdot log p(x)=\frac{1}{2} \cdot log2+\frac{1}{4} \cdot log4+\frac{1}{8} \cdot log8+\frac{1}{8} \cdot log8=1.75 $$

在二进制计算机中,一个比特为0或1(代表二元问题)。在计算机中,我们给哪一匹马夺冠这个事件进行编码,所需要的平均码长为1.75个比特。其定义为:

$$ L(C)=\sum_{x \in X}p(x)l(x) $$

为了尽可能减少码长,我们要给发生概率p(x)较大的事件,分配较短的码长l(x)。所以那么 $${A,B,C,D}$$ 四个实践,可以分别由 $${0,10,110,111}$$ 表示. (1)信息熵只反映内容的随机性,与内容本身无关。不管是什么样内容的文件,只要服从同样的概率分布,就会计算得到同样的信息熵。 (2)信息熵越大,表示占用的二进制位越长,因此就可以表达更多的符号。所以,人们有时也说,信息熵越大,表示信息量越大。不过,由于第一点的原因,这种说法很容易产生误导。较大的信息熵,只表示可能出现的符号较多,并不意味着你可以从中得到更多的信息。 (3)信息熵与热力学的熵,基本无关。

相对熵(KL离散度)

相对熵又叫做KL离散度,其定义为: $$ KL(f(x)||g(x))=-\sum_{x \in X} f(x) \cdot log\frac{f(x)}{g(x)} $$ KL 散度是两个概率分布f(x)和g(x)差别的非对称性的度量。KL散度是用来度量使用基于f(x)的编码来编码来自g(x)的样本平均所需的额外的位元数。 很容易证明,有三个结论: (1) 两函数完全相同时,KL=0 (2) KL越大,差异越大 (3) 对概率分布或者概率密度函数(>0), KL可用来衡量两个随机变量分布的差异性。

交叉熵

对一随机事件,其真实概率分布为p(i),从数据中得到的概率分布为q(i),则我们定义,交叉熵为: $$ H(p,q)=\displaystyle\sum _{x}p(x)log\frac{1}{q(x)}=-\sum _{x}p(x)logq(x) $$

核心理解: * 用p来衡量识别一个样本的信息量即最小编码长度(信息熵)。

$$ H(p)=\sum p \cdot log\frac{1}{p} $$

  • q来估计真实分布为p的样本的信息量.

$$ H(q,p)=\sum p \cdot \frac{1}{q} $$

  • 则估算多出来的冗余信息量.

$$ D(p||q)=H(p,q)-H(p)=\sum p \cdot log\frac{p}{q}(KL离散度) $$

在机器学习中,p通常设定为真实标记的分布,q设定为训练后模型预测标记的分布:

$$ H(p,q)=H(p)+D_{KL}(pq) $$

即:交叉熵=信息熵+KL散度(相对熵) 由于信息熵H(p)H(p)是固定不变的,因此我们在机器学习中就用交叉熵作为损失函数。常见的做法是先用Softmax函数将神经网络的结果转换为概率分布,然后用交叉熵刻画估算的概率分布与真实的概率分布的"距离"。