港口货轮需要进行集装箱的装卸任务:
船上的每一个集装箱,可以用三个维度的坐标来唯一定位:(bay, column, layer),这三个维度结合其他一些固有信息,构成了一个箱子的字段属性,存储在箱子数据表中。
现在需要以bay为单位,对bay内所有column、layer下的箱子,按照特有作业优先级进行作业顺序的编号(优先级从高到低:40尺-单钩箱子>20尺-双钩箱子>20尺-单钩箱子)。
即某个bay下,所有column最上层的箱子,统计他们的优先级,取其优先级最高的特定优先级进行作业,等到所有column最高层的箱子没有该优先级的箱子,按照低一级的优先级进行作业。如此循环往复三个优先级,直到所有的箱子都被编上作业顺序。
大意如此,细节上的约束限制条件,不展开描述
不用双层遍历的算法难度太大,构思不出来
for lay in layers:
for col in columns:
pass
# 老版
for lay in layers:
for col in lay_columns[lay]:
boxes_selected = temp_queryset.filter(box_column=col, box_layer=lay)
# ========================================
len_boxes_selected = boxes_selected.count()
# ========================================
if len_boxes_selected == 2:
if boxes_selected[0].is_work_together == 1:
self.boxes_number_1(boxes_selected)
else:
self.boxes_number_2(boxes_selected)
elif len_boxes_selected == 1:
self.boxes_number_1(boxes_selected)
else:
pass
# 新版
for lay in layers:
for col in lay_columns[lay]:
boxes_selected = temp_queryset.filter(box_column=col, box_layer=lay)
# ========================================
len_boxes_selected = len(boxes_selected)
# ========================================
if len_boxes_selected == 2:
if boxes_selected[0].is_work_together == 1:
self.boxes_number_1(boxes_selected)
else:
self.boxes_number_2(boxes_selected)
elif len_boxes_selected == 1:
self.boxes_number_1(boxes_selected)
else:
pass
对计数后的查询集进行修改操作,用len()函数要比count()函数,效率高一点
参考文章:https://blog.csdn.net/qq_39187019/article/details/108170726
# 老版
layer = [86, 84, 82, 80, 78, 76]
column = [16, 14, 12, 10, 8, 6, 4, 2, 0, 1, 3, 5, 7, 9, 11, 13, 15]
# 新版
layer = [86, 84, 82, 80, 78, 76]
column = {
86:[16, 14, 12, 10, 8, 6, 4, 2, 0, 1, 3, 5, 7, 9, 11, 13, 15],
84:[14, 12, 10, 8, 6, 4, 2, 0, 1, 3, 5, 7, 9, 11],
82:[16, 14, 12, 10, 8, 6, 4, 2, 0, 1, 3, 5, 7, 9, 11, 13, 15],
80:[10, 8, 6, 4, 2, 0, 1, 3, 5, 7, 9, 11, 13, 15],
78:[16, 14, 12, 10, 8, 6, 4, 2, 0, 1, 3, 5, 7, 9, 11, 13, 15],
76:[16, 14, 12, 10, 8, 6, 4, 2, 0, 1, 3, 5, 7]
}
老版:获取这个bay下所有箱子里面,涉及到的列和层
- 该方法十分方便的获取列和层
- 但是存在冗余,特定列,特定层下是没有箱子的,比如:(84, 16)
新版:获取这个bay下所有箱子里面,涉及到的层,再获取特定层下面涉及到的列信息
- 该方法相较于老版,在获取列信息上会更加耗时
- 但是不存在冗余,只要是遍历到的层、列,就一定能保证有箱子
整体计算下来,新版更加节省时间
# 老版本
self.numbered_boxes |= changed_queryset
# 新版本
for box in changed_queryset:
self.numbered_boxes.append(box)
老版:对已经编号的箱子集合进行并集操作
- 最终的存储结果:
新版:在对箱子编号的时候,对箱子进行append操作
- 最终的存储结果:[
, , …]
上述改动,都是逐一改变的,每次改变都会有时间上的节省。
下边仅展示最终结果
版本 | 运算时长(s) |
---|---|
老版 | 316 |
新版 | 143 |
老版
新版