DL4J与Torch、Theano、TensorFlow、Caffe、Paddle、MxNet、Keras 和 CNTK的比较
与其他深度学习框架相比,Deeplearning4j在API语言、宗旨和集成性方面独具特色。DL4J是基于JVM、聚焦行业应用且提供商业支持的**分布式深度学习框架**,能在合理的时间内解决各类涉及大量数据的问题。DL4J与Kafka、Hadoop和Spark集成,可使用任意数量的GPU或CPU运行,而且发生任何问题都可以联系服务热线。
DL4J是一种跨平台的便携式学习库,并非专门针对AWS、Azure或谷歌云等任何一种特定的云端服务而优化。论速度,DL4J用多GPU运行非平凡图像处理任务时的性能可媲美Caffe,优于TensorFlow和Torch。如需对Deeplearning4j运行基准测试,请参阅此页的指南,通过调整JVM的堆空间、垃圾回收算法、内存管理以及DL4J的ETL数据加工管道来优化DL4J的性能。Deeplearning4j拥有Java、Scala和Python API(所用的Python API为Keras)。
目录
Lua
Torch 和 Pytorch
Torch 是用Lua编写的带API的计算框架,支持机器学习算法。Facebook和Twitter等大型科技公司使用Torch的某些版本,由内部团队专门负责定制自己的深度学习平台。Lua是上世纪九十年代早期在巴西开发的多范式脚本语言。
Torch7虽然功能强大,但其设计并不适合在两个群体中大范围普及,即主要依赖Python的学术界,以及普遍使用Java的企业软件工程师。Deeplearning4j用Java编写,反映了我们对行业应用和使用便利的重视。我们认为可用性是阻碍深度学习实施工具广泛普及的限制因素。我们认为可扩展性应当通过 Hadoop 和 Spark 这样的开源分布式运行时系统来实现自动化。我们还认为,从确保工具正常运作和构建社区两方面来看,提供商业支持的开源框架是最恰当的解决方案。
Facebook于2017年1月开放了Torch的Python API ― PyTorch的源代码。PyTorch 支持动态计算图,让您能处理长度可变的输入和输出,而这在RNN应用和其他一些情形中很有帮助。CMU 的 DyNet 和 PFN 的 Chainer 框架也支持动态计算图。
利与弊:
+ 大量模块化组件,容易组合+ 很容易编写自己的层类型并在GPU上运行
+ Lua - 大多数学习库的代码是Lua,比较易读
+ 有很多已预训练的模型!
+ PyTorch
- Lua
- 通常需要自己编写训练代码(即插即用相对较少)
- 不提供商业支持
- 文档质量参差不齐
Python框架
Theano及其生态系统
深度学习领域的许多学术研究者依赖 Theano,Theano是深度学习框架中的元老,用 Python 编写。Theano和NumPy一样,是处理多维数组的学习库。Theano可与其他学习库配合使用,非常适合数据探索和研究活动。
现在已有大量基于Theano的开源深度学习库,包括 Keras、 Lasagne 和 Blocks。这些学习库试着在Theano有时不够直观的接口之上添加一层便于使用的API。(截至2016年3月,另一个与Theano相关的学习库 Pylearn2似乎已经停止开发。)
相比之下,Deeplearning4j致力于将深度学习引入生产环境,以Java和Scala等JVM语言开发解决方案。力求以可扩展、多个GPU或CPU并行的方式让尽可能多的控制点实现自动化,在需要时与Hadoop和 Spark 集成。
利与弊:
+ Python + NumPy+ 计算图是良好的抽象化方式
+ 原始的Theano级别偏低
+ RNN与计算图匹配良好
+ 高级的包装(Keras、Lasagne)减少了使用时的麻烦
- 原始的Theano级别偏低
- 错误信息可能没有帮助
- 大型模型的编译时间可能较长
- 比Torch笨重许多
- 对已预训练模型的支持不够完善
- 在AWS上容易出现bug
- 只支持单个GPU
TensorFlow
- 谷歌开发了TensorFlow来取代Theano,这两个学习库其实很相似。有一些Theano的开发者在谷歌继续参与了TensorFlow的开发,其中包括后来加入了OpenAI 的 Ian Goodfellow。
- 目前TensorFlow还不支持所谓的“内联(inline)”矩阵运算,必须要复制矩阵才能对其进行运算。复制非常大的矩阵会导致成本全面偏高。TF运行所需的时间是最新深度学习工具的四倍。谷歌表示正在解决这一问题。
- 和大多数深度学习框架一样,TensorFlow是用一个Python API编写的,通过C/C++引擎加速。虽然它对Java API有实验性支持,但目前它是是非常不稳定的,这种解决方案并不适合Java和Scala用户群。
- TensorFlow运行明显比其他框架慢(例如:CNTK 和 MxNet)
- TensorFlow的用途不止于深度学习。TensorFlow其实还有支持强化学习和其他算法的工具。
- 谷歌似乎已承认TensorFlow的目标包括招募人才,让其研究者的代码可以共享,推动软件工程师以标准化方式应用深度学习,同时为谷歌云端服务带来更多业务――TensorFlow正是为该服务而优化的。
- TensorFlow不提供商业支持,而谷歌也不太可能会从事支持开源企业软件的业务。谷歌的角色是为研究者提供一种新工具。
- 和Theano一样,TensforFlow会生成计算图(如一系列矩阵运算,例如z = sigmoid(x),其中x和z均为矩阵),自动求导。自动求导很重要,否则每尝试一种新的神经网络设计就要手动编写新的反向传播算法,没人愿意这样做。在谷歌的生态系统中,这些计算图会被谷歌大脑用于高强度计算,但谷歌还没有开放相关工具的源代码。TensorFlow可以算是谷歌内部深度学习解决方案的一半。
- 从企业的角度看,许多公司需要思考的问题在于是否要依靠谷歌来提供这些工具。
- 注意:有部分运算在TensorFlow中的运作方式与在NumPy中不同。
利与弊:
+ Python + NumPy+ 与Theano类似的计算图抽象化
+ 编译时间快于Theano
+ 用TensorBoard进行可视化
+ 同时支持数据并行和模型并行
- 速度比其他框架慢
- 比Torch笨重许多;更难理解
- 不提供商业支持
- 已预训练的模型不多
- 加载每个新的训练批次时都要跳至Python
- 不太易于工具化
- 动态类型在大型软件项目中容易出错
Caffe
Caffe 是一个广为人知、广泛应用的机器视觉库,将Matlab实现的快速卷积网络移植到了C和C++平台上(参见Steve Yegge关于一个芯片一个芯片地移植C++代码的博客,可以帮助你思考如何在速度和这种特定的技术债务之间进行权衡)。Caffe不适用于文本、声音或时间序列数据等其他类型的深度学习应用。与本文提到的其他一些框架相同,Caffe选择了Python作为其API。
Deeplearning4j和Caffe都可以用卷积网络进行图像分类,这是最先进的技术。与Caffe不同,Deeplearning4j支持任意芯片数的GPU并行运行,并且提供许多看似微不足道,却能使深度学习在多个并行GPU集群上运行得更流畅的功能。虽然在论文中被广泛引述,但Caffe主要用于为其Model Zoo网站提供已预训练的模型。
利与弊:
+ 适合前馈网络和图像处理+ 适合微调已有的网络
+ 无需编写任何代码即可训练模型
+ Python接口相当有用
- 需要用C++ / CUDA编写新的GPU层
- 不适合循环网络
- 用于大型网络(GoogLeNet、ResNet)时过于繁琐
- 不可扩展,有些不够精简
- 不提供商业支持
- 更新缓慢,可能以后不再更新
Caffe2
令业界翘首以盼的Caffe2将接替原版Caffe。Caffe的开发人目前在Facebook就职。Caffe2是继Torch/PyTorch之后第二个得到Facebook支持的深度学习框架。从目前的宣传来看,Caffe2的主要区别似乎是更加轻便且可扩展性更强。与Caffe和PyTorch一样,Caffe2提供一个在C++引擎上运行的Python API。
利与弊:
+ BSD许可协议- 不提供商业支持
CNTK
CNTK是微软的开源深度学习框架。CNTK的全称是“计算网络工具包。”此学习库包括前馈DNN、卷积网络和循环网络。CNTK提供基于C++代码的Python API。虽然CNTK遵循一个比较宽松的许可协议,却并未采用ASF 2.0、BSD或MIT等一些较为传统的许可协议。这一许可协议不适用于CNTK旨在简化分布式训练的1-Bit随机梯度下降(SGD)方法,该组件不得用作商业用途。
Chainer
Chainer是一个带有Python API的开源神经网络框架,其核心开发团队隶属于东京一家名叫Preferred Networks的机器学习创业公司,团队工程师主要来自东京大学。在CMU的DyNet和Facebook的PyTorch问世以前,Chainer是最领先的动态计算图神经网络框架。动态计算图能处理可变长度的输入,很适合进行自然语言分析任务。Chainer自己的基准测试发现,该框架的速度明显快于包括MxNet和CNTK在内的其他面向Python的学习框架,而TensorFlow的速度最慢。
DSSTNE
亚马逊的深度可伸缩稀疏张量网络引擎又称DSSTNE,是用于机器学习和深度学习建模的学习库。它是在TensorFlow和CNTK之后较晚发布的不少开源深度学习库之一,后来亚马逊开始以AWS力挺MxNet,所以DSSTNE的发展前景不太明朗。DSSTNE主要用C++写成,速度较快,不过吸引到的用户群体规模尚不及其他学习库。
利与弊:
+ 可实现稀疏编码- 亚马逊可能没有共享示例运行结果最优化所必需的全部信息
- 亚马逊已决定在AWS上使用另一个框架。
DyNet
DyNet亦称动态神经网络工具包,由卡纳基梅隆大学推出,过去曾被称为cnn。它最值得一提的功能就是动态计算图,能够处理可变长度的输入,很适合自然语言分析。PyTorch和Chainer也提供同样的功能。
+ 动态计算图- 用户群较小
Keras
Keras 是一个基于Theano和TensorFlow的深度学习库,具有一个受Torch启发、较为直观的API。这可能是目前最好的Python API。Deeplearning4j可以导入Keras模型。Keras是由谷歌软件工程师Francois Chollet开发的。
+ 受Torch启发的直观API+ 可使用Theano、TensorFlow和Deeplearning4j后端(即将推出CNTK后端)
+ 该框架正快速成长
+ 有可能成为用于开发神经网络的标准Python API
MxNet
MxNet是一个提供多种API的机器学习框架,主要面向R、Python和Julia等语言,目前已被亚马逊云服务采用。据传Apple在2016收购Graphlab/Dato/Turi后,有些部门也开始使用MxNet。MxNet是一个快速灵活的学习库,由华盛顿大学的Pedro Domingos及其研究团队运作。MxNet与Deeplearning4j某些方面的比较参见此处。
Paddle
Paddle是由百度开发支持的深度学习框架,全名为PArallel Distributed Deep LEarning,即 “并行分布式深度学习”。Paddle是最新发布的大型深度学习框架;与多数框架一样,它提供一个Python API。
BigDL
BigDL 是一个新的深度学习框架,重点面向Apache Spark且只能在英特尔处理器上运行。
许可
上述开源项目的另一区别在于其许可协议:Theano、Torch和Caffe采用BSD许可协议,未能解决专利和专利争端问题。Deeplearning4j和ND4J采用Apache 2.0许可协议发布。该协议包含专利授权和防止报复性诉讼的条款,也就是说,任何人都可以自由使用遵循Apache 2.0协议的代码创作衍生作品并为其申请专利,但如果对他人提起针对原始代码(此处即DL4J)的专利权诉讼,就会立即丧失对代码的一切专利权。(换言之,这帮助你在诉讼中进行自我防卫,同时阻止你攻击他人。)BSD一般不能解决这个问题。
JVM相关因素
速度
Deeplearning4j依靠ND4J进行基础的线性代数运算,事实表明其处理大矩阵乘法的速度至少是NumPy的两倍。这正是DL4J被NASA的喷气推进实验室所采用的原因之一。此外,Deeplearning4j为多芯片运行而优化,支持采用CUDA C的x86和GPU。
虽然Torch7和DL4J都采用并行运行,DL4J的并行运行是自动化的。我们实现了从节点(worker nodes)和连接的自动化设置,让用户在Spark、Hadoop或Akka和AWS环境中建立大型并行网络时可以绕过学习库。Deeplearning4j最适合快速解决具体问题。
Deeplearning4j的所有功能参见功能介绍。
为什么选择JVM?
经常有人问,既然有如此之多的深度学习用户都专注于Python,为什么我们要开发一个面向JVM的开源深度学习项目。的确,Python有着优越的语法要素,可以直接将矩阵相加,而无需像Java那样先创建显式类。Python还有由Theano、NumPy等原生扩展组成的广泛的科学计算环境。
但JVM及其主要语言Java和Scala仍然具备几项优势。
首先,多数大型企业和政府机构高度依赖Java或基于JVM的系统。他们已经进行了巨大的投资,而基于JVM的人工智能可以帮助他们充分实现这些投资的价值。在企业界,Java依然是应用范围最广的语言。Java是Hadoop、ElasticSearch、Hive、Lucene和Pig的语言,而它们恰好都是解决机器学习问题的有用工具。Spark和Kafka则是用另一种JVM语言Scala编写的。也就是说,深度学习本可以帮助许多需要解决现实问题的程序员,但他们却被语言屏障阻碍。我们希望提高深度学习对于这一广大群体的可用性,这些新的用户可以将深度学习直接付诸实用。Java是世界上用户规模最大的编程语言,共有1000万名开发者使用Java。
其次,与Python相比,Java和Scala在速度上具有先天优势。如不考虑依赖用Cython加速的情况,任何用Python写成的代码在根本上速度都相对较慢。不可否认,运算量最大的运算都是用C或C++语言编写的。(此处所说的运算也包括高级机器学习流程中涉及的字符和其他任务。)大多数最初用Python编写的深度学习项目在用于生产时都必须重新编写。Deeplearning4j依靠JavaCPP从Java中调用预编译的本机C++代码,大幅提升训练速度。许多Python程序员选择用Scala实现深度学习,因为他们在进行共享基本代码的合作时更青睐静态类型和函数式编程。
第三,为了解决Java缺少强大的科学计算库的问题,我们编写了ND4J。ND4J在分布式CPU或GPU上运行,可以通过Java或Scala的API进行对接。
最后,Java是一种安全的网络语言,本质上具有跨平台的特点,可在Linux服务器、Windows和OSX桌面、安卓手机上运行,还可通过嵌入式Java在物联网的低内存传感器上运行。Torch和Pylearn2通过C++进行优化,优化和维护因而存在困难,而Java则是“一次编写,随处运行”的语言,适合需要在多个平台上使用深度学习系统的企业。
生态系统
生态系统也是为Java增添人气的优势之一。Hadoop是用 Java 实施的;Spark在 Hadoop 的 Yarn 运行时中运行;Akka等开发库让我们能够为 Deeplearning4j 开发分布式系统。总之,对几乎所有应用而言,Java的基础架构都经过反复测试,用Java编写的深度学习网络可以靠近数据,方便广大程序员的工作。Deeplearning4j 可以作为YARN的应用来运行和预配。
Scala、Clojure、Python 和 Ruby等其他通行的语言也可以原生支持 Java。我们选择Java,也是为了尽可能多地覆盖主要的程序员群体。
虽然Java的速度不及 C 和 C++,但它仍比许多人想象得要快,而我们建立的分布式系统可以通过增加节点来提升速度,节点可以是 GPU 或者 CPU。也就是说,如果要速度快,多加几盒处理器就好了。
最后,我们也在用 Java 为 DL4J 打造 NumPy 的基本应用,其中包括 ND-Array。我们相信 Java 的许多缺点都能很快克服,而其优势则大多会长期保持。
Scala
我们在打造 Deeplearning4j 和 ND4J 的过程中特别关注Scala,因为我们认为Scala具有成为数据科学主导语言的潜力。用Scala API为JVM编写数值运算、向量化和深度学习库可以帮助整个群体向实现这一目标迈进。
关于DL4J与其他框架的不同之处,也许只需要尝试一下就能有深入的体会。
机器学习框架
上文提到的深度学习框架都是比较专业化的框架,此外还有许多通用型的机器学习框架。这里列举主要的几种:
- sci-kit learn-Python的默认开源机器学习框架。
- Apache Mahout-Apache的主打机器学习框架。Mahout可实现分类、聚类和推荐。
- SystemML-IBM的机器学习框架,可进行描述性统计、分类、聚类、回归、矩阵参数化和生存分析,还包括支持向量机。
- 微软DMTK-微软的分布式机器学习工具包。分布式词嵌入和LDA。