我有一个由1个master(namenode,secondarynamenode,resourcemanager)和2个slave(datanode,nodemanager)组成的小集群。
我已在master的yarn-site.xml中设置:
yarn.scheduler.minimum-allocation-mb
:512 yarn.scheduler.maximum-allocation-mb
:1024 yarn.scheduler.minimum-allocation-vcores
:1 yarn.scheduler.maximum-allocation-vcores
:2 我已经设置了奴隶的yarn-site.xml:
yarn.nodemanager.resource.memory-mb
:2048 yarn.nodemanager.resource.cpu-vcores
:4 然后在master中,我已经设置了mapred-site.xml:
mapreduce.map.memory.mb
:512 mapreduce.map.java.opts
: - Xmx500m mapreduce.map.cpu.vcores
:1 mapreduce.reduce.memory.mb
:512 mapreduce.reduce.java.opts
: - Xmx500m mapreduce.reduce.cpu.vcores
:1 因此我的理解是,在运行作业时,mapreduce ApplicationMaster将尝试在两个从站上创建512 Mb和1 vCore的容器,每个从站只有2048 Mb和4个vCore,这为4个空间提供了空间每个奴隶上的容器。这正是我工作中发生的事情,所以到目前为止没问题。
但是,当我将mapreduce.map.cpu.vcores
和mapreduce.reduce.cpu.vcores
从1增加到2时,理论上应该只有足够的vCore可用于为每个奴隶创建2个容器吗?但不,我每个奴隶仍有4个容器。
然后我尝试将mapreduce.map.memory.mb
和mapreduce.reduce.memory.mb
从512增加到768.这为2个容器留出了空间(2048/768 = 2)。
如果将vCore设置为1或2用于映射器和缩减器,这将无关紧要,这将始终为每个从站生成2个容器,其中768mb和4个512mb容器。那么vCores是为了什么? ApplicationMaster似乎并不关心。
此外,当将内存设置为768并将vCores设置为2时,我在nodemanager UI上显示此信息以用于映射器容器:
768 Mb已变为1024 TotalMemoryNeeded,并且2个vCores被忽略并显示为1 TotalVCoresNeeded。
所以要打破"它如何运作"提问多个问题:
mapreduce.map.memory.mb
值是否只是用于计算容器数量的完全抽象值(以及它为什么可以向上舍入为2的下一个幂)?或者它是否以某种方式表示真实的内存分配?mapreduce.map.java.opts
中指定一些-Xmx值?为什么不使用mapreduce.map.memory.mb
的值来为容器分配内存?mapreduce.map.cpu.vcores
,但它永远不会更改。答案 0 :(得分:11)
我将回答这个问题,假设调度程序使用的是 CapacityScheduler 。
CapacityScheduler 使用 ResourceCalculator 来计算应用程序所需的资源。有两种类型的资源计算器:
默认情况下,CapacityScheduler使用 DefaultResourceCalculator 。如果您想使用 DominantResourceCalculator ,则需要在“ capacity-scheduler.xml ”文件中设置以下属性:
<property>
<name>yarn.scheduler.capacity.resource-calculator</name>
<value>org.apache.hadoop.yarn.util.resource.DominantResourceCalculator</value>
</property>
现在,回答你的问题:
如果使用 DominantResourceCalculator ,则会考虑内存和VC来计算容器数量
mapreduce.map.memory.mb 不是抽象值。在计算资源时要考虑到这一点。
DominantResourceCalculator 类有一个normalize()函数,它使用minimumResouce(由config yarn.scheduler.minimum-allocation-mb 确定)规范化资源请求, maximumresource(由config yarn.scheduler.maximum-allocation-mb 确定)和步长因子(由config yarn.scheduler.minimum-allocation-mb 确定)。
规范化内存的代码如下所示(检查org.apache.hadoop.yarn.util.resource.DominantResourceCalculator.java):
int normalizedMemory = Math.min(roundUp(
Math.max(r.getMemory(), minimumResource.getMemory()),
stepFactor.getMemory()),maximumResource.getMemory());
其中:
r =请求的内存
逻辑如下:
一个。取最大值(请求的资源和最小资源)= max(768,512)= 768
湾综述(768,StepFactor)= roundUp(768,512)== 1279(大约)
Roundup does : ((768 + (512 -1)) / 512) * 512
℃。 min(roundup(512,stepFactor),maximumresource)= min(1279,1024)= 1024
所以最后,分配的内存是1024 MB,这就是你得到的。
为了简单起见,你可以说综述,以512 MB(这是最小资源)的步长增加需求
mapreduce.map.memory.mb 的位置是容器使用的总内存。
mapreduce.map.java.opts 的值应小于 mapreduce.map.memory.mb
使用 DominantResourceCalculator 时,它使用normalize()函数计算所需的vCore。
该代码(类似于内存规范化):
int normalizedCores = Math.min(roundUp
` Math.max(r.getVirtualCores(), minimumResource.getVirtualCores()),
stepFactor.getVirtualCores()), maximumResource.getVirtualCores());