BroadcastManager用于将配置信息和序列化后的RDD、Job以及ShuffleDependency等信息在本地存储。如果为了容灾,也会复制到其他节点上。创建BroadcastManager的代码实现如下。
val broadcastManager = new BroadcastManager(isDriver, conf, securityManager)
BroadcastManager除了构造器定义的三个成员属性外,BroadcastManager内部还有三个成员,分别是:
- initialized:表示BroadcastManager是否初始化完成的状态。
- broadcastFactory:广播工厂实例。
- nextBroadcastId:下一个广播对象的广播ID。类型为AtomicLong。
BroadcastManager在其初始化的过程中就会调用自身的initialize方法,当initialize执行完毕,BroadcastManager就正式生效。BroadcastManager的initialize方法的实现见代码清单1。
代码清单1 BroadcastManager的初始化
private def initialize() {
synchronized {
if (!initialized) {
broadcastFactory = new TorrentBroadcastFactory
broadcastFactory.initialize(isDriver, conf, securityManager)
initialized = true
}
}
}
根据代码清单1,initialize方法首先判断BroadcastManager是否已经初始化,以保证BroadcastManager只被初始化一次。新建TorrentBroadcastFactory作为BroadcastManager的广播工厂实例。之后调用TorrentBroadcastFactory的initialize方法对TorrentBroadcastFactory进行初始化[1]。最后将BroadcastManager自身标记为初始化完成状态。
注意:TorrentBroadcastFactory实现了BroadcastFactory特质。在Spark 1.x.x版本中,BroadcastManager的initialize方法是使用Java反射生成广播工厂实例broadcastFactory的,还可以通过配置属性spark.broadcast.factory指定BroadcastFactory特质的实现类,默认为org.apache.spark. broadcast.TorrentBroadcastFactory。从Spark 2.0.0版本开始,不再提供此Spark属性,属性成员broadcastFactory也固定为TorrentBroadcastFactory。
BroadcastManager中提供了三个方法,见代码清单2。
代码清单2 BroadcastManager中的三个方法
def stop() {
broadcastFactory.stop()
}
private val nextBroadcastId = new AtomicLong(0)
def newBroadcast[T: ClassTag](value_ : T, isLocal: Boolean): Broadcast[T] = {
broadcastFactory.newBroadcast[T](value_, isLocal, nextBroadcastId.getAndIncrement())
}
def unbroadcast(id: Long, removeFromDriver: Boolean, blocking: Boolean) {
broadcastFactory.unbroadcast(id, removeFromDriver, blocking)
}
从代码清单2可以看到BroadcastManager的三个方法都分别代理了TorrentBroadcastFactory的对应方法,TorrentBroadcastFactory中提供的三个方法的实现见代码清单3。
代码清单3 TorrentBroadcastFactory提供的方法
override def newBroadcast[T: ClassTag](value_ : T, isLocal: Boolean, id: Long): Broadcast[T] = {
new TorrentBroadcast[T](va