使用过渡属性优先处理附近的访问

此示例展示了如何使用转接属性来确定路线的优先级,在这种情况下,同一辆车会在同一时间段内执行附近的接人和送货服务。如需详细了解转换属性,请参阅使用转换属性对业务逻辑进行建模

在此示例中:

  • 订单 A、B 和 C 的送货地址位于同一道路上,相距不远。
  • 我们后续还会推出更多版本。
  • 送货没有指定送货时间。
  • 无论上门服务时间表如何,车辆都需要沿此道路行驶两次:一次是在上午从车库出发时,另一次是在晚上返回时。
  • 无论何时执行 A、B 和 C,路线的总行程距离和时长始终相同。

在同一道路上配送多个商品的示例。有三笔运输订单 A、B 和 C 正在从仓库运往其他运输订单。A 距离车库 1000 米,B 距离车库 50 米,C 在同一方向上比 B 还要远 30 米。还有其他配送地址距离 C 有 1,000 米。

在这种情况下,对于仅使用每小时费用和每公里费用的请求,优化后的路线可能会在早上处理 A 和 B,并在晚上处理 C,并且解决方案的费用与同时处理这三项的费用相同。

设有阈值的每公里费用

如需对附近的光顾进行分组,您首先需要选择一个阈值距离。这是您认为是“附近”的两次光顾之间的最大距离。此示例使用 100 米的阈值,大致相当于城市区域的一个街区。您可以提高或降低此阈值,以满足您的业务需求和驾驶员的偏好设置。

如需将相距 100 米的附近访问进行分组,您可以为每次转换的前 100 米设置较高的费用,并为转换的任何其他米数设置较低的费用。由于前 100 米的费用最高,因此优化器会使用短于 100 米阈值的过渡,即使这意味着延长路线的总长度,也能最大限度地节省费用。

如需设置费用,请向 ShipmentModel.transition_attributes 添加一个新条目,并为其设置以下属性:

{
  "model": {
    "transitionAttributes": [
      {
        "excluded_dst_tag": "UNUSED_TAG",
        "excluded_src_tag": "UNUSED_TAG",
        "distanceLimit": {
          "softMaxMeters": 100,
          "costPerKilometerBelowSoftMax": 50,
          "costPerKilometerAboveSoftMax": 1,
        }
      }
    ]
  }
}

任何运输或车辆都不得使用标记 #unused_tag# 来匹配所有可能的转换。如需了解详情,请参阅如何匹配所有访问请求

低于阈值的费用较高的情况的运作方式

本部分将介绍低于和高于阈值的费用如何影响示例场景中不同解决方案的总费用。

解决方案 1:在去程执行 A、B,在回程执行 C

在此解决方案中,运输会拆分为对此道路的两次遍历。其中两个在第一次遍历时传送,其余一个在第二次遍历时传送。转换有 5 种:

过渡 距离 低于阈值 高于阈值
距离 费用 距离 费用
车库 →A 1000 米 100 m 5 900 米 0.9
A→B 50 米 50 米 2.5 0 分钟 0
B→other 1030 米 100 m 5 930 米 0.93
其他 → C 1000 米 100 m 5 900 米 0.9
C→depot 1080 米 100 m 5 980 米 0.98
总计 450 米 22.5 3710 米 3.71

总费用是每公里这两项费用的总和:

  • 低于阈值 (50) 的每公里费用乘以低于阈值的总行驶距离 (450 米 = 0.45 公里),
  • 超出阈值的每公里费用 (1) 乘以超出阈值的总行驶距离 (3710 米 = 3.71 公里)。

因此,总费用为 0.45 * 50 + 3.71 * 1 = 22.5 + 3.71 = 26.21。

解决方案 2:在去往目的地途中执行 A、B、C,在返回途中不执行任何操作

与解决方案 1 不同,在此解决方案中,所有三笔运输都是在一次穿越道路期间“作为一组”进行配送。在另一次穿越中,车辆完全不会停车。同样,有 5 个转场效果,但它们的长度和组成不同:

过渡 距离 低于阈值 高于阈值
距离 费用 距离 费用
车库 →A 1000 米 100 m 5 900 米 0.9
A→B 50 米 50 米 2.5 0 分钟 0
B→C 30 米 30 米 1.5 0 分钟 0
C→other 1000 米 100 m 5 900 米 0.9
其他→仓库 2080 m 100 m 5 1980 米 1.98
总计 380 米 19 3780 m 3.78

使用与解决方案 1 中相同的计算方法,总费用为 0.38 * 50 + 3.78 * 1 = 19 + 3.78 = 22.78,在一个时间段内执行所有访问的费用低于分两组执行。您可以通过增加 DistanceLimit.cost_per_kilometer_below_soft_max 来增强此效果。

为什么低于阈值的每公里费用较低

由于您希望短途转接优先于长途转接,因此您可能会倾向于为长途转接设置较高的每公里费用,并为短途转接设置较低的每公里费用。但这实际上会产生相反的效果:由于过渡的前 100 米是最便宜的,因此优化器会优先选择接近或超过 100 米的过渡,以便充分利用这些“便宜”的米数。

您可以在两个示例解决方案中看到这种效果。如果您将低于阈值和高于阈值的每公里费用互换,路线费用会发生变化:

费用高于阈值 低于阈值的费用较高
解决方案 1 解决方案 2 解决方案 1 解决方案 2
低于阈值的公里数 0.45 0.38 0.45 0.38
每公里费用低于阈值 1.00 1.00 50.00 50.00
超出阈值的公里数 3.71 3.78 3.71 3.78
超出阈值的每公里费用 50.00 50.00 1.00 1.00
总费用 185.95 189.38 26.21 22.78

对于每个版本,系统会将两种解决方案的总费用中较低者以粗体突出显示。您可以看到,如果您使用高于阈值的费用,则将会提高将访问次数分组的路线的总费用,这与您想要实现的目标相反。