מגבלות על חלון הזמנים של איסוף ומסירה

OptimizeToursRequest מחילה מגבלות על:

  • משלוחים, שמשפיעים על אופן ביצוע המשלוחים
  • כלי רכב, שמשפיעים על אופן החישוב של מסלולי כלי רכב
  • השפעה גלובלית על כלי רכב ועל משלוחים.

המדריך הזה מתמקד במגבלות משלוח חיוניות: חלונות זמן.

חלונות זמן הם סוג האילוץ שאתם מספקים בהודעה של OptimizeToursRequest (REST, gRPC) כדי לציין מגבלות מבוססות-זמן לפעילויות המשלוח. סוג האילוץ הזה משפיע גם על המועד ועל האופן שבו אפשר לבצע את המשלוח, וגם על הקצאת הרכב למשלוח. בעזרת המגבלות האלה, כלי האופטימיזציה ייתן עדיפות לרכבים שיכולים לעמוד במגבלות הזמן של המשלוח בצורה הטובה ביותר.

מגבלות משלוח: חלונות זמן

כדי לציין מתי איסוף או מסירה יכולים להתבצע בהודעה Shipment.VisitRequest:

  • שימוש במאפיין timeWindows בהודעה (REST, gRPC)
  • מציינים את שעת ההתחלה ושעת הסיום בהודעת TimeWindow (REST, gRPC).

דוגמה לבקשה עם מגבלות של חלון זמן

בדוגמה כאן רואים שלוש משלוחים שונים, ולכל אחד מהם יש חלון זמן משלו למשלוח. כדי לשמור על הסבר פשוט, בדוגמה הזו מגדירים חלונות זמן ב-deliveries בלבד, אבל אפשר להחיל חלונות זמן גם על איסוף. אפשר לציין כמה חלונות זמן, אבל בדוגמה הזו אפשר להשתמש רק באחד לכל משלוח VisitRequest.

הצגת בקשה לדוגמה עם חלונות זמן

{
  "populatePolylines": false,
  "populateTransitionPolylines": false,
  "model": {
    "globalStartTime": "2023-01-13T16:00:00Z",
    "globalEndTime": "2023-01-14T16:00:00Z",
    "shipments": [
      {
        "deliveries": [
          {
            "arrivalLocation": {
              "latitude": 37.789456,
              "longitude": -122.390192
            },
            "duration": "250s",
            "timeWindows": [
              {
                "startTime": "2023-01-13T18:00:00Z",
                "endTime": "2023-01-13T19:00:00Z"
              }
            ]
          }
        ],
        "pickups": [
          {
            "arrivalLocation": {
              "latitude": 37.794465,
              "longitude": -122.394839
            },
            "duration": "150s"
          }
        ],
        "penaltyCost": 100.0
      },
      {
        "deliveries": [
          {
            "arrivalLocation": {
              "latitude": 37.789116,
              "longitude": -122.395080
            },
            "duration": "250s",
            "timeWindows": [
              {
                "startTime": "2023-01-13T18:00:00Z",
                "endTime": "2023-01-13T18:30:00Z"
              }
            ]
          }
        ],
        "pickups": [
          {
            "arrivalLocation": {
              "latitude": 37.794465,
              "longitude": -122.394839
            },
            "duration": "150s"
          }
        ],
        "penaltyCost": 20.0
      },
      {
        "deliveries": [
          {
            "arrivalLocation": {
              "latitude": 37.795242,
              "longitude": -122.399347
            },
            "duration": "250s",
            "timeWindows": [
              {
                "startTime": "2023-01-13T17:30:00Z",
                "endTime": "2023-01-13T18:00:00Z"
              }
            ]
          }
        ],
        "pickups": [
          {
            "arrivalLocation": {
              "latitude": 37.794465,
              "longitude": -122.394839
            },
            "duration": "150s"
          }
        ],
        "penaltyCost": 50.0
      }
    ],
    "vehicles": [
      {
        "endLocation": {
          "latitude": 37.794465,
          "longitude": -122.394839
        },
        "startLocation": {
          "latitude": 37.794465,
          "longitude": -122.394839
        },
        "costPerHour": 40.0,
        "costPerKilometer": 10.0
      }
    ]
  }
}
    

דוגמה לתגובה עם מגבלות של חלון זמן

בתגובה לדוגמה, זמני ההתחלה והסיום של הרכב הם 17:35:50 ו-18:17:24 בהתאמה. הזמנים האלה משקפים את האופטימיזציה שמפחיתה את הזמן שנדרש לתפעול הרכב שצוין בבקשה כ-costPerHour, תוך עמידה בכל המגבלות של חלון הזמן. שימוש בשעה 17:35:50 כשעת התחלה מבטל את הצורך שהרכב ימתין במיקום הביקור עד שיתחיל חלון הזמן של הביקור. הערך מופיע בתשובה כאפס ערכי waitDuration.

הצגת תשובה לבקשה לדוגמה עם חלונות זמן

{
  "routes": [
    {
      "vehicleStartTime": "2023-01-13T17:35:50Z",
      "vehicleEndTime": "2023-01-13T18:17:24Z",
      "visits": [
        {
          "isPickup": true,
          "startTime": "2023-01-13T17:35:50Z",
          "detour": "0s"
        },
        {
          "shipmentIndex": 1,
          "isPickup": true,
          "startTime": "2023-01-13T17:38:20Z",
          "detour": "150s"
        },
        {
          "shipmentIndex": 2,
          "isPickup": true,
          "startTime": "2023-01-13T17:40:50Z",
          "detour": "300s"
        },
        {
          "shipmentIndex": 2,
          "startTime": "2023-01-13T17:50:09Z",
          "detour": "0s"
        },
        {
          "shipmentIndex": 1,
          "startTime": "2023-01-13T18:00:00Z",
          "detour": "796s"
        },
        {
          "startTime": "2023-01-13T18:07:35Z",
          "detour": "1520s"
        }
      ],
      "transitions": [
        {
          "travelDuration": "0s",
          "waitDuration": "0s",
          "totalDuration": "0s",
          "startTime": "2023-01-13T17:35:50Z"
        },
        {
          "travelDuration": "0s",
          "waitDuration": "0s",
          "totalDuration": "0s",
          "startTime": "2023-01-13T17:38:20Z"
        },
        {
          "travelDuration": "0s",
          "waitDuration": "0s",
          "totalDuration": "0s",
          "startTime": "2023-01-13T17:40:50Z"
        },
        {
          "travelDuration": "409s",
          "travelDistanceMeters": 1371,
          "waitDuration": "0s",
          "totalDuration": "409s",
          "startTime": "2023-01-13T17:43:20Z"
        },
        {
          "travelDuration": "341s",
          "travelDistanceMeters": 1312,
          "waitDuration": "0s",
          "totalDuration": "341s",
          "startTime": "2023-01-13T17:54:19Z"
        },
        {
          "travelDuration": "205s",
          "travelDistanceMeters": 636,
          "waitDuration": "0s",
          "totalDuration": "205s",
          "startTime": "2023-01-13T18:04:10Z"
        },
        {
          "travelDuration": "339s",
          "travelDistanceMeters": 1276,
          "waitDuration": "0s",
          "totalDuration": "339s",
          "startTime": "2023-01-13T18:11:45Z"
        }
      ],
      "metrics": {
        "performedShipmentCount": 3,
        "travelDuration": "1294s",
        "waitDuration": "0s",
        "delayDuration": "0s",
        "breakDuration": "0s",
        "visitDuration": "1200s",
        "totalDuration": "2494s",
        "travelDistanceMeters": 4595
      },
      "routeCosts": {
        "model.vehicles.cost_per_hour": 27.711111111111112,
        "model.vehicles.cost_per_kilometer": 45.95
      },
      "routeTotalCost": 73.661111111111111
    }
  ],
  "metrics": {
    "aggregatedRouteMetrics": {
      "performedShipmentCount": 3,
      "travelDuration": "1294s",
      "waitDuration": "0s",
      "delayDuration": "0s",
      "breakDuration": "0s",
      "visitDuration": "1200s",
      "totalDuration": "2494s",
      "travelDistanceMeters": 4595
    },
    "usedVehicleCount": 1,
    "earliestVehicleStartTime": "2023-01-13T17:35:50Z",
    "latestVehicleEndTime": "2023-01-13T18:17:24Z",
    "totalCost": 73.661111111111111,
    "costs": {
      "model.vehicles.cost_per_hour": 27.711111111111112,
      "model.vehicles.cost_per_kilometer": 45.95
    }
  }
}
    

חלונות הזמן הזמינו את visits של הרכב כדי שהמשלוחים עם חלונות הזמן המוקדמים ביותר יימסרו ראשונים.

  1. shipments[2] נמסר בשעה 17:50
  2. מסירת shipments[1] בשעה 18:00
  3. shipments[0] נמסר בשעה 18:07

הבקשה לדוגמה מציינת מגבלות קשות על חלון זמן, ומחייבות להשלים את המסירה בחלונות האלה. אם השלמת VisitRequests של משלוח בחלון הזמן כלשהו לא אפשרית או משתלמת, כלי האופטימיזציה מדלג על המשלוח. אם המשלוח כולל penaltyCost, כלי האופטימיזציה מוסיף אותו לעלויות שמדווחות בתגובה metrics. אחרת, המאפיין skippedMandatoryShipmentCount של הודעת OptimizeToursResponse (REST, gRPC) גדל.

אם תשנו את חלונות הזמן על ידי שינוי החלון של shipment[1] כמה שעות מאוחר יותר (ל-21:00 מ-18:00), התוצאות יהיו שונות כפי שמתואר בדוגמאות הבאות.

הצגת בקשה לדוגמה עם חלונות זמן שאי אפשר לעמוד בהם

{
  "populatePolylines": false,
  "populateTransitionPolylines": false,
  "model": {
    "globalStartTime": "2023-01-13T16:00:00Z",
    "globalEndTime": "2023-01-14T16:00:00Z",
    "shipments": [
      {
        "deliveries": [
          {
            "arrivalLocation": {
              "latitude": 37.789456,
              "longitude": -122.390192
            },
            "duration": "250s",
            "timeWindows": [
              {
                "startTime": "2023-01-13T18:00:00Z",
                "endTime": "2023-01-13T19:00:00Z"
              }
            ]
          }
        ],
        "pickups": [
          {
            "arrivalLocation": {
              "latitude": 37.794465,
              "longitude": -122.394839
            },
            "duration": "150s"
          }
        ],
        "penaltyCost": 100.0
      },
      {
        "deliveries": [
          {
            "arrivalLocation": {
              "latitude": 37.789116,
              "longitude": -122.395080
            },
            "duration": "250s",
            "timeWindows": [
              {
                "startTime": "2023-01-13T21:00:00Z",
                "endTime": "2023-01-13T21:30:00Z"
              }
            ]
          }
        ],
        "pickups": [
          {
            "arrivalLocation": {
              "latitude": 37.794465,
              "longitude": -122.394839
            },
            "duration": "150s"
          }
        ],
        "penaltyCost": 20.0
      },
      {
        "deliveries": [
          {
            "arrivalLocation": {
              "latitude": 37.795242,
              "longitude": -122.399347
            },
            "duration": "250s",
            "timeWindows": [
              {
                "startTime": "2023-01-13T17:30:00Z",
                "endTime": "2023-01-13T18:00:00Z"
              }
            ]
          }
        ],
        "pickups": [
          {
            "arrivalLocation": {
              "latitude": 37.794465,
              "longitude": -122.394839
            },
            "duration": "150s"
          }
        ],
        "penaltyCost": 50.0
      }
    ],
    "vehicles": [
      {
        "endLocation": {
          "latitude": 37.794465,
          "longitude": -122.394839
        },
        "startLocation": {
          "latitude": 37.794465,
          "longitude": -122.394839
        },
        "costPerHour": 40.0,
        "costPerKilometer": 10.0
      }
    ]
  }
}
    

הצגת תשובה לבקשה השנייה לדוגמה עם חלונות זמן שבהם מדלגים על משלוח

{
  "routes": [
    {
      "vehicleStartTime": "2023-01-13T17:37:49Z",
      "vehicleEndTime": "2023-01-13T18:09:49Z",
      "visits": [
        {
          "isPickup": true,
          "startTime": "2023-01-13T17:37:49Z",
          "detour": "0s"
        },
        {
          "shipmentIndex": 2,
          "isPickup": true,
          "startTime": "2023-01-13T17:40:19Z",
          "detour": "150s"
        },
        {
          "shipmentIndex": 2,
          "startTime": "2023-01-13T17:49:38Z",
          "detour": "0s"
        },
        {
          "startTime": "2023-01-13T18:00:00Z",
          "detour": "946s"
        }
      ],
      "transitions": [
        {
          "travelDuration": "0s",
          "waitDuration": "0s",
          "totalDuration": "0s",
          "startTime": "2023-01-13T17:37:49Z"
        },
        {
          "travelDuration": "0s",
          "waitDuration": "0s",
          "totalDuration": "0s",
          "startTime": "2023-01-13T17:40:19Z"
        },
        {
          "travelDuration": "409s",
          "travelDistanceMeters": 1371,
          "waitDuration": "0s",
          "totalDuration": "409s",
          "startTime": "2023-01-13T17:42:49Z"
        },
        {
          "travelDuration": "372s",
          "travelDistanceMeters": 1348,
          "waitDuration": "0s",
          "totalDuration": "372s",
          "startTime": "2023-01-13T17:53:48Z"
        },
        {
          "travelDuration": "339s",
          "travelDistanceMeters": 1276,
          "waitDuration": "0s",
          "totalDuration": "339s",
          "startTime": "2023-01-13T18:04:10Z"
        }
      ],
      "metrics": {
        "performedShipmentCount": 2,
        "travelDuration": "1120s",
        "waitDuration": "0s",
        "delayDuration": "0s",
        "breakDuration": "0s",
        "visitDuration": "800s",
        "totalDuration": "1920s",
        "travelDistanceMeters": 3995
      },
      "routeCosts": {
        "model.vehicles.cost_per_kilometer": 39.95,
        "model.vehicles.cost_per_hour": 21.333333333333332
      },
      "routeTotalCost": 61.283333333333331
    }
  ],
  "skippedShipments": [
    {
      "index": 1
    }
  ],
  "metrics": {
    "aggregatedRouteMetrics": {
      "performedShipmentCount": 2,
      "travelDuration": "1120s",
      "waitDuration": "0s",
      "delayDuration": "0s",
      "breakDuration": "0s",
      "visitDuration": "800s",
      "totalDuration": "1920s",
      "travelDistanceMeters": 3995
    },
    "usedVehicleCount": 1,
    "earliestVehicleStartTime": "2023-01-13T17:37:49Z",
    "latestVehicleEndTime": "2023-01-13T18:09:49Z",
    "totalCost": 81.283333333333331,
    "costs": {
      "model.shipments.penalty_cost": 20,
      "model.vehicles.cost_per_hour": 21.333333333333332,
      "model.vehicles.cost_per_kilometer": 39.95
    }
  }
}
    

בדוגמה הזו, חלון הזמן המאוחר יותר גרם לדילוג על shipment[1], כי זמן ההפעלה הנוסף של הרכב שנדרש כדי להשלים את מסירת המשלוח במסגרת חלון הזמן שצוין חרג מדמי המשלוח. עלות הקנס על shipment[1] מופיעה בmetrics.costs, והמדד שלו מופיע ב-skippedShipments.

מגבלות לחלון זמן רך

כפי שצוין בקצרה בקטע פרמטרים של מודל עלות, אפשר להחיל חלונות זמן כמגבלות רכות. מגבלות רכות שונות ממגבלות קשות באופן הבא:

  • מגבלות קשיחות: אי אפשר להפר את המגבלה, וכלי האופטימיזציה לא מציע פתרון שמפר את המגבלה, גם אם המשמעות היא לדלג על משלוח.
  • מגבלות רכות: ייתכן שיש הפרה, כלומר כלי האופטימיזציה עשוי לספק פתרון שמפר מגבלה רכה. עם זאת, כלי האופטימיזציה מחיל עלות גם על כל הפרה. את העלות הזו מספקים כמאפיין נוסף בחלון הזמן, בדרך כלל כעלות לשעה בכל שעה לפני או אחרי חלון הזמן שבו הפעילות מתרחשת.

חלונות הזמן מרככים את חלונות הזמן באמצעות softStartTime או softEndTime במקום startTime או endTime בהתאמה, ועל ידי הגדרה של costPerHourBeforeSoftStartTime או costPerHourAfterSoftEndTime.

השתמשו באילוצים של חלון זמן קצר כאשר איסוף או משלוחים אמורים להתרחש במסגרת חלון זמן מסוים, אבל איסוף או מסירה במסגרת חלון הזמן הזה לא נדרשים לחלוטין. אתם יכולים להשתמש באילוצים של חלונות זמן קשים ורך יחד כדי לבטא יעדים עסקיים. למשל:

  • חלון זמן קשה: מציין את שעות הפעילות של הלקוח, למשל מ-9:00 עד 17:00.
  • חלון זמן רך: מציין את מסגרת הזמן למשלוח או לאיסוף שתואמת להודעה שנשלחה ללקוח, למשל בין 09:00 ל-13:00.

בדוגמה הזו, המשלוח שדילג עליו בעבר כי חלון הזמן שלו התחיל מאוחר מדי, רירך את מגבלת שעת ההתחלה. זמני הסיום של חלונות הזמן האחרים ריככו גם כן.

הצגת בקשה לדוגמה עם חלונות של שעות מוקשות ורך

{
  "populatePolylines": false,
  "populateTransitionPolylines": false,
  "model": {
    "globalStartTime": "2023-01-13T16:00:00Z",
    "globalEndTime": "2023-01-14T16:00:00Z",
    "shipments": [
      {
        "deliveries": [
          {
            "arrivalLocation": {
              "latitude": 37.789456,
              "longitude": -122.390192
            },
            "duration": "250s",
            "timeWindows": [
              {
                "startTime": "2023-01-13T18:00:00Z",
                "softEndTime": "2023-01-13T19:00:00Z",
                "costPerHourAfterSoftEndTime": 2.0
              }
            ]
          }
        ],
        "pickups": [
          {
            "arrivalLocation": {
              "latitude": 37.794465,
              "longitude": -122.394839
            },
            "duration": "150s"
          }
        ],
        "penaltyCost": 100.0
      },
      {
        "deliveries": [
          {
            "arrivalLocation": {
              "latitude": 37.789116,
              "longitude": -122.395080
            },
            "duration": "250s",
            "timeWindows": [
              {
                "softStartTime": "2023-01-13T21:00:00Z",
                "endTime": "2023-01-13T21:30:00Z",
                "costPerHourBeforeSoftStartTime": 2.0
              }
            ]
          }
        ],
        "pickups": [
          {
            "arrivalLocation": {
              "latitude": 37.794465,
              "longitude": -122.394839
            },
            "duration": "150s"
          }
        ],
        "penaltyCost": 20.0
      },
      {
        "deliveries": [
          {
            "arrivalLocation": {
              "latitude": 37.795242,
              "longitude": -122.399347
            },
            "duration": "250s",
            "timeWindows": [
              {
                "startTime": "2023-01-13T17:30:00Z",
                "softEndTime": "2023-01-13T18:00:00Z",
                "costPerHourAfterSoftEndTime": 2.0
              }
            ]
          }
        ],
        "pickups": [
          {
            "arrivalLocation": {
              "latitude": 37.794465,
              "longitude": -122.394839
            },
            "duration": "150s"
          }
        ],
        "penaltyCost": 50.0
      }
    ],
    "vehicles": [
      {
        "endLocation": {
          "latitude": 37.794465,
          "longitude": -122.394839
        },
        "startLocation": {
          "latitude": 37.794465,
          "longitude": -122.394839
        },
        "costPerHour": 40.0,
        "costPerKilometer": 10.0
      }
    ]
  }
}
    

הצגת תשובה לבקשה לדוגמה עם חלונות זמן לפגישות ביניים

{
  "routes": [
    {
      "vehicleStartTime": "2023-01-13T17:48:35Z",
      "vehicleEndTime": "2023-01-13T18:24:28Z",
      "visits": [
        {
          "isPickup": true,
          "startTime": "2023-01-13T17:48:35Z",
          "detour": "0s"
        },
        {
          "shipmentIndex": 1,
          "isPickup": true,
          "startTime": "2023-01-13T17:51:05Z",
          "detour": "150s"
        },
        {
          "shipmentIndex": 2,
          "isPickup": true,
          "startTime": "2023-01-13T17:53:35Z",
          "detour": "300s"
        },
        {
          "startTime": "2023-01-13T18:00:00Z",
          "detour": "300s"
        },
        {
          "shipmentIndex": 1,
          "startTime": "2023-01-13T18:07:42Z",
          "detour": "493s"
        },
        {
          "shipmentIndex": 2,
          "startTime": "2023-01-13T18:17:27Z",
          "detour": "873s"
        }
      ],
      "transitions": [
        {
          "travelDuration": "0s",
          "waitDuration": "0s",
          "totalDuration": "0s",
          "startTime": "2023-01-13T17:48:35Z"
        },
        {
          "travelDuration": "0s",
          "waitDuration": "0s",
          "totalDuration": "0s",
          "startTime": "2023-01-13T17:51:05Z"
        },
        {
          "travelDuration": "0s",
          "waitDuration": "0s",
          "totalDuration": "0s",
          "startTime": "2023-01-13T17:53:35Z"
        },
        {
          "travelDuration": "235s",
          "travelDistanceMeters": 795,
          "waitDuration": "0s",
          "totalDuration": "235s",
          "startTime": "2023-01-13T17:56:05Z"
        },
        {
          "travelDuration": "212s",
          "travelDistanceMeters": 791,
          "waitDuration": "0s",
          "totalDuration": "212s",
          "startTime": "2023-01-13T18:04:10Z"
        },
        {
          "travelDuration": "335s",
          "travelDistanceMeters": 1204,
          "waitDuration": "0s",
          "totalDuration": "335s",
          "startTime": "2023-01-13T18:11:52Z"
        },
        {
          "travelDuration": "171s",
          "travelDistanceMeters": 665,
          "waitDuration": "0s",
          "totalDuration": "171s",
          "startTime": "2023-01-13T18:21:37Z"
        }
      ],
      "metrics": {
        "performedShipmentCount": 3,
        "travelDuration": "953s",
        "waitDuration": "0s",
        "delayDuration": "0s",
        "breakDuration": "0s",
        "visitDuration": "1200s",
        "totalDuration": "2153s",
        "travelDistanceMeters": 3455
      },
      "routeCosts": {
        "model.shipments.deliveries.time_windows.cost_per_hour_after_soft_end_time": 0.58166666666666667,
        "model.shipments.deliveries.time_windows.cost_per_hour_before_soft_start_time": 5.7433333333333332,
        "model.vehicles.cost_per_hour": 23.922222222222221,
        "model.vehicles.cost_per_kilometer": 34.55
      },
      "routeTotalCost": 64.797222222222217
    }
  ],
  "metrics": {
    "aggregatedRouteMetrics": {
      "performedShipmentCount": 3,
      "travelDuration": "953s",
      "waitDuration": "0s",
      "delayDuration": "0s",
      "breakDuration": "0s",
      "visitDuration": "1200s",
      "totalDuration": "2153s",
      "travelDistanceMeters": 3455
    },
    "usedVehicleCount": 1,
    "earliestVehicleStartTime": "2023-01-13T17:48:35Z",
    "latestVehicleEndTime": "2023-01-13T18:24:28Z",
    "totalCost": 64.797222222222217,
    "costs": {
      "model.vehicles.cost_per_kilometer": 34.55,
      "model.shipments.deliveries.time_windows.cost_per_hour_before_soft_start_time": 5.7433333333333332,
      "model.shipments.deliveries.time_windows.cost_per_hour_after_soft_end_time": 0.58166666666666667,
      "model.vehicles.cost_per_hour": 23.922222222222221
    }
  }
}
    

כאשר בדוגמה עם מגבלות של חלון זמן קשיח בלבד דילגת על shipment[1], ריכוך חלון זמן האספקה גורם לכך שהיא נמסרת לפני שעת ההתחלה של חלון הזמן. באופן דומה, ריכוך זמני הסיום של משלוחים אחרים אפשרה מסירה של shipment[2] אחרי שחלון הזמן שלו מסתיים.

במקביל, השתנו העלויות וסך כל המשלוחים:

  • totalCost: ירידה מ-81.283 ל-64.797
  • סה"כ משלוחים שהושלמו: גדל מ-2 ל-3

כלי האופטימיזציה מצא פתרון זול יותר כי מגבלות חלון הזמן היו רגועות יותר בהשוואה לדוגמה הקודמת.

לבסוף, המאפיין metrics.costs כולל גם מפתח חדש כדי לציין את העלות בפועל שנצברו על סמך המכפלה של האילוץ ומשך הזמן שבו חלון המסירה היה חסר. כלומר:

  • costPerHourBeforeSoftStartTime מתוך 2.0 ו-
  • משך הזמן בין המסירה בפועל לבין תחילת חלון הזמן: 2.83583 שעות

תוצאה:

model.shipments.deliveries.time_windows.cost_per_hour_before_soft_start_time: 5.6716666666666669.

בעזרת המדדים האלה אפשר לבצע ניתוח עלויות כדי למצוא את יחסי הגומלין בין מגבלות קשוחות לבין מגבלות רכות, ולהשתמש בהן כדי להתאים את האילוצים לכללים העסקיים הספציפיים שלכם. במקרה הזה, העלות הכוללת תהיה פחות מ-shipment[1].penalty_cost של 20.0. צוות האופטימיזציה זיהה שחסכוני יותר לספק את המשלוח מוקדם יותר מאשר לדלג על המשלוח.