<颠覆大数据分析 基于StormSpark等Hadoop替代技术的实时应用>

为什么要超越Hadoop MapReduce

Hadoop的适用范围

  • Hadoop缺乏对象数据库连接(ODBC)
  • Hadoop不适合所有类型的应用程序
    • hadoop不适合分片数据
    • Hadoop不适合迭代式计算

海量数据分析所需的计算范式分类(7大任务)

  1. 基础分析
  2. 线性代数计算
  3. 广义的多体问题
  4. 图论问题
  5. 优化
  6. 积分
  7. 比对问题

Hadoop非常适合第一类基础分析,对于其他问题,较简单或者小型的任务都是Hadoop可解的。

于是有了Spark,spark可以看做是大数据领域下一个数据处理的Hadoop的替代品。

spark能支持下面这些:

  • 复杂的线性代数问题—任务2
  • 泛化多体问题–任务3,比如核SVM和核PCA
  • 某些优化问题–任务4,比如设计共轭梯度法的问题。

spark与众不同的一点在于它的内存计算,它允许在各迭代/交互间将数据缓存到内存中。

  • 需要超越Hadoop进行思考的一个方面是迭代式机器学习,Spark是一项可选的技术。
  • 需要超越Hadoop进行思考的另一个方面是在于实时分析,可以选择Storm及Spark streaming
  • 需要超越Hadoop进行思考的第三个因素在于一些特定的负责数据结构需要进行专门的处理–图就是一个例子。GraphLab是大图形处理方面的一个重要范式。

三代机器学习工具

  1. 传统的机器学习和数据分析工具,包括SAS、SPSS、Weka以及R语言
  2. 第二代包括Mahout、Pentaho、RapidMiner、RHadoop
  3. 第三代,如Spark、Twister Storm、HaLoop、Hama、GraphLab等 迭代式机器学习算法、实时分析、图形处理

共轭梯度法CGD是迭代计算的最佳典范,每一个CGD都可以分解成daxpy,ddot、matmul等原语。

伯克利数据分析栈BDAS

实现动机

关键组成部分,Mesos、Spark、Shark

实现BDAS的动机 — Hadoop MapReduce的局限性

Spark动机

Spark是BDAS框架的核心。

  • Spark的一个主要动机就是希望能以一种无缝的方式使用Scala的集合或者序列进行分布式编程。

Shark动机

Shark的动机 – 为了大规模分析中交互式查询。

解决海量数据集上交互式查询的方式大致可分为两类

  • 并行数据库
  • Hadoop MapReduce

MapReduce和并行数据库的不同之处:

  • schema
  • 效率
  • 容错性

基于并行数据库和MapReduce的缺点,Shark的目标就是要实现一个基于分布式的SQL查询框架,并能提供高性能且丰富的分析能力(与并行数据库相比),以及细粒度的恢复能力(与MapReduce相比)。

Mesos动机

  • 对集群资源进行监控并且能足够快速地获取它们的信息。
  • 通过共享模式能够将多个框架同时运行在同一集群环境中。

BDAS设计和架构

整个架构分为三层–资源管理层、数据管理层及数据处理层。

  • 第一层管理的是可用资源,包括集群的节点以及有效地管理资源的能力。常用的包括Mesos、Hadoop Yarn以及Nimbus
  • 第二层是数据管理层,通常是由一个分布式文件系统来实现的。
  • 第三层是数据处理层,Spark是这一层的关键框架。
  • 第四层是应用程序层

Spark:高效的集群数据处理范式

你会发现Hadoop MapReduce中每次迭代都会涉及到HDFS的读写,而在Spark中要简单的多,它仅需从HDFS到Spark的分布式共享对象空间中进行一次读入—从HDFS文件中创建RDD(弹性分布式数据集 Resilient Distributed Datasets)。RDD可以重用,在机器学习的各个迭代中,它都会驻留在内存中,这样能显著提高性能。当检查结束条件发现迭代结束时,会将RDD持久化,把数据写回到HDFS中。

Spark的弹性分布式数据集RDD

RDD能够让用户操作分布式系统上的Scala集合。Spark中的这个Scala集合就是RDD。

Spark程序只能拥有一个RDD引用,它知道自己的世系,包括它是如何创建的、上面执行了哪些操作。世系为RDD提供了容错性—即使它丢失了,只要世系本身被持久化或者复制了,就仍能重建整个RDD。

在RDD上可以执行许多操作,包括count、collect及save。

下面是一个RDD编程示例,介绍如何在Spark环境下进行RDD编程:

RDD间有两种类型的依赖关系:窄依赖和宽依赖。

Spark的实现

当触发RDD上的一个动作时,一个被称为有向无环图DAG调度器的Spark组件就会检查RDD的世系图,同时会创建各阶段的DAG。每一个阶段都只会出现窄依赖,宽依赖所需的洗牌操作就是阶段的边界。调取器在DAG的不同阶段启动任务来计算缺失的分区,以便重构整个RDD对象。它将各阶段的任务独享提交给任务调度器TS。任务对象是一个独立的实体,它由代码和转换以及所需的元数据组成。调度器还负责重新提交那些输出丢失了的阶段。任务调度器使用一个被称为延迟调度的调度算法来将任务分配给各个节点。如果RDD中指定了优先区域,任务就会被传送给这些节点,否则会被分配到那些有分区在请求内存任务的节点上。对于宽依赖而言,中间记录会在那些包含父分区的节点上生成。这样会使得错误回复变得简单,Hadoop MapReduce中的map输出的物化也是类似的。

Spark中的Worker组件负责接收任务对象并在一个线程池中调用它们的run方法。它将异常或者错误报告给TaskSetManager TSM。TSM是任务调度器管理的一个实体,每个任务集都会对应一个TSM,用于跟踪任务的执行过程。TS是按照先进先出FIFO的顺序来轮询TSM集的。通过插入不同的策略或者算法,这里仍有一定的优化空间。执行器会与其他组件进行交互,比如块管理器BM、通信管理器CM、Map输出跟踪器MOT。块管理器是节点用于缓存RDD并接收洗牌数据的组件。它也可以看做是每个Worker中只写一次的K-V键值存储。块管理器和通信管理器进行通信以便获取远端的块数据。通信管理器是一个异步网络库。MOT这个组件会负责跟踪每个map任务的运行位置并把这些信息返回给规约器–worker会缓存这些信息。弱映射器的输出丢失,会使用一个“分代id”来将这些缓存置为无效。

RDD的存储可以通过如下三种方式来完成。

  • 作为java虚拟机中的反序列化的Java对象
  • 作为内存汇总该序列化的java对象
  • 存储在磁盘上

一旦内存满了,Spark的内存管理会通过最近最少使用LRU策略来回收RDD。

Spark和分布式共享内存系统DSM

  • DSM允许单独读写内存,Spark只允许进行粗粒度的RDD抓换。
  • DSM需要检查点相互协作来完成容错,而Spark只需要存储世系图来进行容错。
  • 由于RDD的只读特性,Spark可以使用流浪者缓解策略,使得备份任务可以并行完成。而在DSM中很难缓解流浪者或者备份任务。
  • 在Spark中,当RDD大小超出集群的所有内存时,可以优雅的进行降级。
  • Spark缺点:由于RDD转换是粗粒度的,这限制了能够开发的应用的种类。

RDD的表达性

可以通过RDD及其相关的操作来表示集群计算模型,列举如下

  • MapReduce
  • DryadLINQ
  • 整体同步并行BSP
  • 迭代式MapReduce

类似Spark系统

Nectar、HaLoop及其Twister等都是类似于Spark的系统。

Shark:分布式系统上的SQL接口

Shark基于Spark提供了SQL接口。Shark的主要特性就是它的SQL接口以及它能够基于机器学习来进行分析的能力。同时还有它为SQL查询和机器学习算法所提供的细粒度的容错性。

Spark为Shark提供的扩展

在Spark的RDD上执行SQL查询遵循传统并行数据库的三部流程:

  1. 查询解析
  2. 逻辑计划的生成
  3. 将逻辑计划映射为物理的执行计划

Shark使用Hive查询编译器来进行查询语句的解析。

部分有向无环图执行PDE

其他特点

  • 列存储存储
  • 分布式数据加载
  • 完全分区智能连接
  • 分区裁剪

机器学习的支持

Shark的一个关键又独特的埋点是它能够支持机器学习算法。能否实现这一关键点是因为Shark云讯在返回查询结果的同时顺便返回代表执行计划的RDD对象。

Mesos:集群调度及管理系统 51

Mesos的主要目标是帮助管理不同的框架或者应用栈间的集群资源。

Mesos是一个双层调度器,在第一层中,Mesos将一定的资源以容器的形式提供给对应的框架。框架在第二层接收到资源后,运行自己的调度算法来将任务分配到Mesos所提供的这些资源上。

Mesos组件 52

Mesos的关键组件是它的主从守护进程。它们分别运行在Mesos的主节点和从节点上。框架或者框架部分都会托管在从节点上,框架部件包括两个进程,执行进程和调度进程。从节点给主节点发布一个可用资源的列表,是以<2CPU 8G内存>列表的形式发布的。主节点会唤起分配模块,它会根据配置策略来给框架分配资源。随后主节点将资源分配给框架调度器。框架调度器接收到这些请求后,会将需要进行的任务列表以及它们所需的资源发送回去。主节点将任务以及资源需求一并发送给从节点,后者会将这些信息发送给框架调度器,框架调度器会负责启动这些任务。集群中剩余的资源可以自由分配给其他的框架。接下来只要现有的任务完成了并且集群中的资源又重新变为可用的,分配资源的过程就会随着时间不断地重复。

资源分配 54

资源分配是可插拔的,目前一共有两种方式实现。

  • 主导资源公平策略DRF
  • ....

隔离 55

Mesos使用linux或者Solaris容器提供了隔离功能。

Mesos使用的是LXC,它通过cgroup进程控制组来进行资源管理,并使用内核命名空间进行隔离。

容错性 57

Mesos为主节点提供容错的方式是使用ZooKeeper的热备用配置来运行多个主节点,一点主节点崩溃,就会选出新的主节点。主节点的状态由三部分组成---活动从节点、活动框架以及运行任务列表。

使用 Spark实现机器学习算法

机器学习基础知识 66

机器学习这个术语指的是数据的模式学习。机器学习可以推断出一组观测数据及对应的响应之间的模式或者说重要的关联关系。

机器学习的一些应用:

  • 语音识别系统
  • 完全领域的脸部识别系统
  • 相关的是否的答案对于过滤垃圾邮件非常有用
  • 命名实体识别–文档实体识别
  • 网页搜索

机器学习:随机森林RF

决策树和随机森林天然就是可并行的,它们非常适合Hadoop。

根据学习问题的种类,机器学习算法那可以分为下面几种。

  • 归纳学习和直推学习
  • 机器学习的方法
    • 监督学习------------带标签
    • 强化学习,增强学习-----------奖励和惩罚机制
    • 无监督学习---------------无标记,包括聚类和降维
  • 机器学习的数据表示----批处理或者在线学习
  • 机器学习的任务--------回归或者分类

逻辑回归:概述 72

逻辑回归LR是迭代式的。LR是一个概率分类模型,它可以用来根据一组自变量来预测因变量的输出。

二元形式的逻辑回归 73

逻辑回归根据特征值来预测比值比,比值比的定义是某个时间发生与不发生的概率比。

逻辑回归估计 75

逻辑回归预测的是概率而不仅仅是分类。意味着,它可以使用一个似然函数来拟合。

多元逻辑回归 76

二元逻辑回归可以泛化为支持多个离散的输出,也成为多元逻辑回归。使用多元逻辑回归实现的分类器通常成为最大熵分类器。

Spark中的逻辑回归算法 77

JavaHdfsLR是逻辑回归算法在Spark中的实现,采用的是渐进梯度下降SGD的模型。

计算流程:

  1. 由HDFS的输入文件创建一个RDD
  2. 使用map函数来转换ParsePoint
  3. 只要输入记录中仍有特征值就不断地进行迭代,最终创建出一个初始的权值列表。
  4. 使用另一个map转来来计算梯度,迭代的次数由用户来指定。

支持向量机 80

支持向量机SVN是用来解决二院分类问题的一个监督式学习方法。

复杂决策面 81

核转换

支持向量机背后的数学原理 82

Spark中的支持向量机 84

Spark中SVMModel的内部类表示训练时过程中返回的模型对象以及SVMWithSGD,它是SVM中的核心实现。

SVM算法的工作流如下:

  1. 创建Spark上下文
  2. 加载已标记的输入训练数据,SVM中用到的标记必须为0,1
  3. 使用由label-feature对及其输入参数组成的RDD输入来训练模型
  4. 使用输入数据创建一个类型为SVMWithSGD的对象
  5. 调用GeneralizedLinearModel重写后的run方法,它会使用预配置的参数在输入RDD的LabeledPoint上进行算法,并对所有输入特征的初始权重进行处理。
  6. 获得一个SVM模型对象
  7. 终止Spark上下文

Spark对 PMML的支持 85

预测模型扩展语言–PMML是分析模型的标准。

PMML是一个基于XML的标准,应用程序可以通过它来描述及传输数据挖掘和机器学习的模型。

数据分析师通常采用传统工具进行建模(SAS/R/SPSS)。这个模型可以保存为PMML文件,并由我们构建的框架来读取,框架能在Spark上以批处理模式对这个保存好的PMML文件进行评分–这使得它得以扩展到集群环境中的大数据集上。框架还可以在Storm或者Spark steaming上以实时模式进行PMML的评分,这样它们的分析模型就可以实时地工作。

PMML结构 87

PMML头

数据字典

数据转换(连续性转换、离散值标准化、离散化、值映射)

模型

挖掘模式

目标及输出

PMML的生产者及消费者 92

PMML的生产者指的是任意能生成PMML文件的实体。传统的数据分析模型工作都属于PMML的生产者。

PMML的消费者是指消费PMML文件并生成预测结果或者评分结果的实体。

JPMML是一款开源的PMML生产者及消费者引擎,完全由java编写。(Pattern、ADAPA)

Spark对朴素贝叶斯的 PMML支持 94

实现对朴素贝叶斯的PMML支持的关键在于,在Spark中实现贝叶斯算法。

在Spark应用程序中执行的过程如下:

  1. 创建一个SAX解释器及一个朴素贝叶斯的处理器对象,他们会根据PMML模型文件来预测分类。
  2. 从输入文件中创建一个Java的RDD。对输入RDD元素进行预处理。
  3. 对RDD处理后获得元素进行遍历,使用步骤1创建的朴素贝叶斯处理器对象来预测他们到底属于哪个分类。
  4. 最后将完成分类过程的时间记录到输出文件。

Spark对线性回归的 PMML支持 95

线性回归算法使用了监督式学习模型来分析标量变量y和记为X的特征值或者解释变量之间的关系。

在Spark应用程序中执行的过程如下:

  1. 从给定的PMML输入文件中加载PMML模型.......
  2. 为了测试模型,会从输入文件中创建一个RDD对象
  3. 使用map方法将生成的RDD进行转换,输入行会按逗号进行分割以获取记录的独立维度......
  4. 在转换之外,在结果RDD上应用一个Spark动作来获取一个预测列表。
  5. 最后将结果以及完成分类时间记录到输出文件。

在 Spark中使用 MLbase进行机器学习 97

MLbase的主要初衷是希望能让更多的人使用机器学习,包括那些没有很强的分布式系统背景或没有太多实现大规模机器学习算法编程经验的人。

MLbase可以看做是一组用于构建新的分布式机器学习算法的原语。

MLbase是基于主从框架的。用户将请求发送到主机上,主机会解析请求并生成一个逻辑学习计划LLP。LLP是一个工作流,它将ML任务或者ML算法及参数的形式展现出来,同事还包括特定的技术及数据采样策略。随后他会将LLP转化为一个物理学习计划PLP,PLP由一系列基于MLbase原语设计的ML操作组成,主机会将PLP分发给一系列的从机来执行。对一个分类任务而言,LLP会先进行二次采样得到一个较小的数据集,然后他会尝试将不同的SVM或者AdaBoost技术和正规化等参数进行组合。初步测试完结果的质量后,他会将LLP转换成PLP,后者会指定一个用于大样本空间上进行训练的合适的算法及参数。

实现实时图处理范式1

Storm简介 101

Storm是一个负责时间处理引擎CEP,最初是由Twitter实现。

Storm可以属猪基本的的流式处理以及基于数据流的机器学习,通常情况下,数据分析(prestorage analytics)在Storm上运行,然后把结果保存在NoSQL后者关系数据库管理系统RDBMS。

数据流 103

Storm的一个基本概念就是数据流,它可以被定义为无级的无界序列。Storm只提供多种去中心化且容错的数据流转换方式。

拓扑 104

在Storm内部,数据流的处理由Storm拓扑来完成。拓扑包含一个spout(数据源),bolt–负责处理来自spout和其他bolt的数据。

bolt执行数据流转换,包含计算、过滤、聚合、连接等,一个拓扑可以有多个bolt,用来完成复杂的转换和聚合。

Storm集群 105

一个Storm集群由主节点和从节点构成。主节点通常运行在Nimbus守护进程。Nimbus守护进程负责在集群中传输代码、分配任务和监控集群健康状态。

每一个从节点运行一个叫做supervisor的守护进程。这是一个工人进程,负责执行拓扑的一部分工作。一个典型的拓扑由运行在多个集群节点中的进程组成。supervisor接受主节点分派的任务后启动工人进程处理。

主从节点之间的协调通信由Zookeeper集群完成。集群状态由Zookeeper集群维护,确保集群的可恢复性,故障发生时可选举出主节点,并继续执行拓扑。

拓扑本身是由spout、bolt,以及他们连接在一起的方式构成的图结果,它与MapReduce任务的主要区别在于MapReduce是短命的,而Storm拓扑一直运行。

简单的实时计算例子 106

open

nextTuple

....

数据流组 108

spout和bolt都可能并行执行多个任务,必须有一种方法指定哪个数据流路由到哪个spout/bolt。数据流组用来指定一个拓扑内必须遵守的路由进程。

Storm的内建的数据流组

  • 随机数据流组
  • 域数据流组
  • 全部数据流组
  • 直接数据流组
  • 本地数据流组
  • 不分组

Storm的消息处理担保 109

从spout生成的远足能够触发进一步的元组分发,基于拓扑和所应用的转换。

在Storm内部,有一组acker任务持续追踪来自每条元组消息的DAG。

基于 Storm的设计模式 111

分布式远程过程调用 111

RPC远程过程调用

客户机发起一次RPC时发生了下面的事件:

  1. 调用环境要么挂起,要么忙等待
  2. 参数被编组并通过网络传输到目的机、服务器或被调用者,也就是程序将要被执行的地方
  3. 参数被整理后,程序在远程节点执行
  4. 远程节点的程序执行结束后,结果被传回客户机或者源。
  5. 客户机程序就像刚从一个本地过程调用返回一样继续执行

DRPC提供了一个在Storm上的分布式RPC实现。基本概念是高度计算密集型的程序可以从RPC的分布式实现中获益,因为计算过程分布到整个Storm集群了。集群通过一个DRPC服务器协调DRPC请求。DRPC服务器接收来自客户端的RPC请求,并把它们分到Storm集群,由集群节点并行地执行程序,DPRC服务器接收来自Storm集群的结果,并用它们相应客户端。

Trident:基于 Storm的实时聚合 115

....

实现基于 Storm的逻辑回归算法 116

LogisticRegressionTopology是基于Storm的一个实现了Mahout逻辑回归的java类。

mahout是一个Apache项目,一种工作在Hadoop集群上的机器学习工具,因而它可以把机器学习算法扩展到大数据集上。

实现基于 Storm的支持向量机算法 120

Storm对朴素贝叶斯 PMML的支持 122

实时分析的应用 126

工业日志分类 126

互联网流量过滤器 130

Storm的替代品 131

Akka、Yahoo的S4,

Spark流 133

D-Streams的动机 133

三个动机

  1. 容错性
  2. 一致性
  3. 与批处理整合

D-Streams计算子(有状态和无状态计算子)

有状态计算子:

  1. 窗口计算子
  2. 增量聚合
  3. 时间左偏连接
  4. 输出计算子

图处理范式 138

Pregel:基于 BSP的图处理框架 139

Pregel是第一个用于图处理的BSP实现。它是由谷歌创建,用于处理社会关系,及其他图标型数据。Pregel的主要动机是没有运行于分布式系统之上的可容错的大型图表处理框架。

在图的初始化阶段,Pregel中的计算包含一个输入阶段,一系列迭代叫做超步。

类似的做法 141

GBASE/Surfer/Pegasus/Stratosphere

开源的 Pregel实现 143

Giraph/GoldenORB/Phoebus/Apache Hama/Stanford GPS/GraphLab/PowerGraph

GraphLab:多核版本

分布式的 GraphLab

通过 GraphLab实现网页排名算法 156

顶点程序 158

基于 GraphLab实现随机梯度下降算法 163

结论:超越Hadoop Map-Reduce的大数据分析 171

Hadoop YARN概览 172

Hadoop YARN的基本架构是从MapReduce框架中分离了资源调度,而这二者在Hadoop1.0是捆绑在一起的。

Hadoop YARN的动机 172

Hadoop1.0的限制主要在以下几个方面:

  • 扩展性
  • 地方性一室
  • 集群效用
  • MapReduce编程模型的局限性

作为资源调度器的 YARN 174

YARN对范式的根本转变是将资源管理从面向具体应用的处理与执行中分离出来。这两个功能的重要组件是资源管理RM和应用主机AM。RM是将集群资源视作统一的视图,并与之一起的整体调度,他负责全局调度。AM根据相关作业执行情况为RM负责具体作业资源征用。

YARN上的其他框架 175

 

大数据分析的未来是怎样的 177

原文地址:https://www.cnblogs.com/LearnFromNow/p/9350320.html

时间: 2024-10-06 14:35:23

<颠覆大数据分析 基于StormSpark等Hadoop替代技术的实时应用>的相关文章

CI框架源码阅读笔记3 全局函数Common.php

从本篇开始,将深入CI框架的内部,一步步去探索这个框架的实现.结构和设计. Common.php文件定义了一系列的全局函数(一般来说,全局函数具有最高的加载优先权,因此大多数的框架中BootStrap引导文件都会最先引入全局函数,以便于之后的处理工作). 打开Common.php中,第一行代码就非常诡异: if ( ! defined('BASEPATH')) exit('No direct script access allowed'); 上一篇(CI框架源码阅读笔记2 一切的入口 index

IOS测试框架之:athrun的InstrumentDriver源码阅读笔记

athrun的InstrumentDriver源码阅读笔记 作者:唯一 athrun是淘宝的开源测试项目,InstrumentDriver是ios端的实现,之前在公司项目中用过这个框架,没有深入了解,现在回来记录下. 官方介绍:http://code.taobao.org/p/athrun/wiki/instrumentDriver/ 优点:这个框架是对UIAutomation的java实现,在代码提示.用例维护方面比UIAutomation强多了,借junit4的光,我们可以通过junit4的

Yii源码阅读笔记 - 日志组件

?使用 Yii框架为开发者提供两个静态方法进行日志记录: Yii::log($message, $level, $category);Yii::trace($message, $category); 两者的区别在于后者依赖于应用开启调试模式,即定义常量YII_DEBUG: defined('YII_DEBUG') or define('YII_DEBUG', true); Yii::log方法的调用需要指定message的level和category.category是格式为“xxx.yyy.z

源码阅读笔记 - 1 MSVC2015中的std::sort

大约寒假开始的时候我就已经把std::sort的源码阅读完毕并理解其中的做法了,到了寒假结尾,姑且把它写出来 这是我的第一篇源码阅读笔记,以后会发更多的,包括算法和库实现,源码会按照我自己的代码风格格式化,去掉或者展开用于条件编译或者debug检查的宏,依重要程度重新排序函数,但是不会改变命名方式(虽然MSVC的STL命名实在是我不能接受的那种),对于代码块的解释会在代码块前(上面)用注释标明. template<class _RanIt, class _Diff, class _Pr> in

CI框架源码阅读笔记5 基准测试 BenchMark.php

上一篇博客(CI框架源码阅读笔记4 引导文件CodeIgniter.php)中,我们已经看到:CI中核心流程的核心功能都是由不同的组件来完成的.这些组件类似于一个一个单独的模块,不同的模块完成不同的功能,各模块之间可以相互调用,共同构成了CI的核心骨架. 从本篇开始,将进一步去分析各组件的实现细节,深入CI核心的黑盒内部(研究之后,其实就应该是白盒了,仅仅对于应用来说,它应该算是黑盒),从而更好的去认识.把握这个框架. 按照惯例,在开始之前,我们贴上CI中不完全的核心组件图: 由于BenchMa

CI框架源码阅读笔记2 一切的入口 index.php

上一节(CI框架源码阅读笔记1 - 环境准备.基本术语和框架流程)中,我们提到了CI框架的基本流程,这里这次贴出流程图,以备参考: 作为CI框架的入口文件,源码阅读,自然由此开始.在源码阅读的过程中,我们并不会逐行进行解释,而只解释核心的功能和实现. 1.       设置应用程序环境 define('ENVIRONMENT', 'development'); 这里的development可以是任何你喜欢的环境名称(比如dev,再如test),相对应的,你要在下面的switch case代码块中

Apache Storm源码阅读笔记

欢迎转载,转载请注明出处. 楔子 自从建了Spark交流的QQ群之后,热情加入的同学不少,大家不仅对Spark很热衷对于Storm也是充满好奇.大家都提到一个问题就是有关storm内部实现机理的资料比较少,理解起来非常费劲. 尽管自己也陆续对storm的源码走读发表了一些博文,当时写的时候比较匆忙,有时候衔接的不是太好,此番做了一些整理,主要是针对TridentTopology部分,修改过的内容采用pdf格式发布,方便打印. 文章中有些内容的理解得益于徐明明和fxjwind两位的指点,非常感谢.

CI框架源码阅读笔记4 引导文件CodeIgniter.php

到了这里,终于进入CI框架的核心了.既然是"引导"文件,那么就是对用户的请求.参数等做相应的导向,让用户请求和数据流按照正确的线路各就各位.例如,用户的请求url: http://you.host.com/usr/reg 经过引导文件,实际上会交给Application中的UsrController控制器的reg方法去处理. 这之中,CodeIgniter.php做了哪些工作?我们一步步来看. 1.    导入预定义常量.框架环境初始化 之前的一篇博客(CI框架源码阅读笔记2 一切的入

jdk源码阅读笔记之java集合框架(二)(ArrayList)

关于ArrayList的分析,会从且仅从其添加(add)与删除(remove)方法入手. ArrayList类定义: p.p1 { margin: 0.0px 0.0px 0.0px 0.0px; font: 18.0px Monaco } span.s1 { color: #931a68 } public class ArrayList<E> extends AbstractList<E> implements List<E> ArrayList基本属性: /** *

dubbo源码阅读笔记--服务调用时序

上接dubbo源码阅读笔记--暴露服务时序,继续梳理服务调用时序,下图右面红线流程. 整理了调用时序图 分为3步,connect,decode,invoke. 连接 AllChannelHandler.connected(Channel) line: 38 HeartbeatHandler.connected(Channel) line: 47 MultiMessageHandler(AbstractChannelHandlerDelegate).connected(Channel) line: