如何在Dyalog APL中无需模拟APL2优雅实现APL2式内积?
Dyalog APL中资源约束产量计算的优雅实现
问题背景
给定两个矩阵:
cross(7×5布尔矩阵):每行对应一种产品,标记该产品需要的资源(1表示需要,0表示不需要)avail(5×8矩阵):每行对应一类资源,每列对应一周的可用容量
核心需求:计算每种产品在每周的最大可能产量——即该产品所需资源在对应周的可用量中的最小值(无需考虑不需要的资源)
APL2中可通过包装复制操作/为函数R,结合内积⌊.R实现,但Dyalog APL直接用⌊./会得到无效结果。以下是无需模拟APL2的直接实现方案:
优雅实现方案
方案1:掩码替换+维度缩减
通过将不需要的资源可用量替换为极大值,避免无效值干扰最小值计算:
⌊/ (1 - cross) × ⊃⍬ + cross × avail
逻辑解释:
⊃⍬表示Dyalog中的无穷大(也可替换为足够大的数值如1e30)(1 - cross) × ⊃⍬将不需要的资源位置设为无穷大,不会影响最终最小值结果cross × avail保留需要的资源的可用量- 两者相加后,
⌊/沿资源维度(第2轴)取最小值,最终得到7×8的结果矩阵,每个元素对应产品在对应周的最大产量
方案2:压缩+逐行取最小值
利用压缩操作筛选出每个产品所需的资源,再逐周取最小值:
↑ ⌊/¨ cross ⊂⍤1 ⊢ ⍉avail
逻辑解释:
⍉avail将avail转置为8×5的周-资源矩阵(每行对应一周的所有资源可用量)cross ⊂⍤1 ⊢ ⍉avail对每个产品的资源需求掩码,从每周的资源可用量中筛选出对应项,得到7个8×n的数组(n为该产品所需资源的数量)⌊/¨对每个产品的数组逐周取最小值,得到7个长度为8的向量↑将向量列表转换为7×8的结果矩阵
方案3:压缩资源行+维度缩减
通过压缩操作提取每个产品对应的资源行,再逐周取最小值:
⌊/⍤2 cross ⌿⍤1 ⊢ avail
逻辑解释:
cross ⌿⍤1 ⊢ avail对每个产品的资源需求掩码,提取avail中对应的资源行,得到7×n×8的三维数组(n为该产品所需资源数)⌊/⍤2沿资源维度取最小值,最终得到7×8的结果矩阵
测试验证
用小尺寸矩阵验证:
cross ← 2 3 ⍴ 1 1 0 0 0 1 ⍝ 产品1需要资源1、2;产品2需要资源3 avail ← 3 2 ⍴ 5 3 4 2 6 1 ⍝ 资源1:周1=5,周2=3;资源2:周1=4,周2=2;资源3:周1=6,周2=1
执行方案1代码:
⌊/ (1 - cross) × ⊃⍬ + cross × avail
输出结果:
4 2 6 1
完全符合预期:产品1周1受限于资源2的4,周2受限于资源2的2;产品2两周分别受限于资源3的6和1。
内容的提问来源于stack exchange,提问作者Adám
相关产品推荐
相关产品推荐

