我有一个8节点集群,我从jdbc源加载两个数据帧,如下所示:
positionsDf = spark.read.jdbc(
url=connStr,
table=positionsSQL,
column="PositionDate",
lowerBound=41275,
upperBound=42736,
numPartitions=128*3,
properties=props
)
positionsDF.cache()
varDatesDf = spark.read.jdbc(
url=connStr,
table=datesSQL,
column="PositionDate",
lowerBound=41275,
upperBound=42736,
numPartitions=128 * 3,
properties=props
)
varDatesDF.cache()
res = varDatesDf.join(positionsDf, on='PositionDate').count()
我可以从应用程序UI的存储选项卡中看到分区均匀分布在群集节点上。但是,我无法分辨的是如何它们在节点之间分布。理想情况下,两个数据帧的分布方式使得连接始终是节点的本地连接,甚至是执行器本地更好的连接。
换句话说,包含PositionDate =“2016年1月1日”记录的positionsDF数据帧分区是否与包含PositionDate =“2016年1月1日”记录的varDatesDf数据帧分区位于同一执行程序内存空间中?他们会在同一个节点上吗?或者它只是随机的?
有没有办法查看哪个分区在哪个节点上?
spark是否以确定的方式跨节点分配使用这样的列密钥创建的分区?他们总是本地的节点/执行者吗?
答案 0 :(得分:0)
包含PositionDate =" 2016年1月1日"的记录的positionsDF数据帧分区将与包含PositionDate =" 01 Jan的记录的varDatesDf数据帧分区位于同一执行程序内存空间中2016"
它不会一般。即使数据是共同分区的(它不在这里),它也不意味着共址。
有没有办法查看哪个分区在哪个节点上?
这种关系不一定要随时间修复。例如,任务可以重新安排。您可以使用不同的AppComponent
技巧(RDD
)或数据库日志,但它不可靠。
将以这样的方式分发:连接始终是节点的本地连接,或者甚至更好地是执行器的本地连接。
Scheduler有内部优化,低级API允许您设置节点首选项,但这种类型的东西在Spark SQL中是不可控制的。