این سناریو ترتیب توقف های اختصاص داده شده به یک وسیله نقلیه را با پارامترهای هزینه ساده بهینه می کند. این سادهترین حالت عملیات بهینهسازی مسیر است و اطمینان میدهد که تمام توقفها در بازه زمانی مشخص شده بازدید میشوند.
مثال زیر یک سناریوی اساسی با یک وسیله نقلیه و سه محموله را نشان میدهد که همگی از یک مکان به نام انبار منشا میگیرند.
نمونه درخواست را ببینید
{ "populatePolylines": true, "populateTransitionPolylines": true, "model": { "globalStartTime": "2023-01-13T16:00:00-08:00", "globalEndTime": "2023-01-14T16:00:00-08:00", "shipments": [ { "deliveries": [ { "arrivalLocation": { "latitude": 37.789456, "longitude": -122.390192 }, "duration": "250s" } ], "pickups": [ { "arrivalLocation": { "latitude": 37.794465, "longitude": -122.394839 }, "duration": "150s" } ] }, { "deliveries": [ { "arrivalLocation": { "latitude": 37.789116, "longitude": -122.395080 }, "duration": "250s" } ], "pickups": [ { "arrivalLocation": { "latitude": 37.794465, "longitude": -122.394839 }, "duration": "150s" } ] }, { "deliveries": [ { "arrivalLocation": { "latitude": 37.795242, "longitude": -122.399347 }, "duration": "250s" } ], "pickups": [ { "arrivalLocation": { "latitude": 37.794465, "longitude": -122.394839 }, "duration": "150s" } ] } ], "vehicles": [ { "endLocation": { "latitude": 37.794465, "longitude": -122.394839 }, "startLocation": { "latitude": 37.794465, "longitude": -122.394839 }, "costPerKilometer": 10.0, "costPerHour": 40.0 } ] } }
فیلدهای درخواست بهینه سازی مسیر
همانطور که در نمای کلی ذکر شد، مهمترین ویژگی درخواست بهینه سازی مسیر vehicles
و shipments
هستند.
درخواست علاوه بر وسیله نقلیه و محموله ها شامل فیلدهای زیر است:
چند خط
populatePolylines
و populateTransitionPolylines
مشخص می کنند که آیا Route Optimization باید چند خطوط را برگرداند یا خیر.
این سرویس Polylines را با استفاده از کدک چند خط Maps JS کدگذاری میکند، که دادههای چند خطی باینری را با استفاده از کاراکترهای قابل چاپ ASCII نشان میدهد. می توانید از ابزار Interactive Polyline Encoder برای تجسم مسیرهای محاسبه شده توسط Route Optimization استفاده کنید. مثال در این راهنما، populatePolylines
و populateTransitionPolylines
را روی true تنظیم می کند، اما راهنماهای دیگر آنها را روی false تنظیم می کنند تا اندازه پاسخ را کاهش دهند.
برای توضیح فرمت کدگذاری ، قالب الگوریتم چند خط رمزگذاری شده را ببینید.
محدودیت های زمانی جهانی
model.globalStartTime
و model.globalEndTime
روی یک دوره 24 ساعته دلخواه تنظیم شده اند. این باعث میشود که مُهرهای زمانی خروجی تفسیر شوند.
از مکان ها دیدن کنید
درخواست نمونه فقط از model.shipments[].pickups[].arrivalLocation
و model.shipments[].deliveries[].arrivalLocation
استفاده می کند. همچنین یک ویژگی departureLocation
برای موقعیتهایی وجود دارد که وسیله نقلیه از نقطهای متفاوت از جایی که میرسد، مانند یک مجتمع پارکینگ با ورودی در یک طرف ساختمان و یک خروجی در سمت دیگر، حرکت میکند. در این راهنما و راهنمای بعدی، نقاط ورود و خروج یکسان فرض شده است.
waypoint
رسیدن و خروج نیز به عنوان جایگزینی برای latLng
وجود دارد. فیلدهای Waypoint
از استفاده از شناسههای Google Place به عنوان جایگزین LatLng
پشتیبانی میکنند و همچنین میتوانند عنوان خودرو را مشخص کنند. برای جزئیات بیشتر به مستندات مرجع ( REST ، gRPC ) مراجعه کنید.
محدودیت ها در مثال
این سناریو از چند جهت بهینه ساز را محدود می کند:
- تمام فعالیت ها باید بین زمان شروع و پایان جهانی تکمیل شود . در این سناریو، زمان شروع و پایان با توجه به نزدیکی محمولهها و پنجره زمانی گسترده جهانی، یک محدودیت بسیار سست است.
- تمام محموله ها باید تکمیل شود . این رفتار پیش فرض زمانی است که هزینه های جریمه در
shipments
مشخص نشده است. -
costPerKilometer
وcostPerHour
روی خودرو تنظیم شده است.
هزینه ها در پارامترهای مدل هزینه پرداخته می شوند.
ویژگی های پاسخ بهینه سازی مسیر
پاسخ به درخواست نمونه را ببینید
{ "routes": [ { "vehicleStartTime": "2023-01-14T00:00:00Z", "vehicleEndTime": "2023-01-14T00:36:41Z", "visits": [ { "shipmentIndex": 2, "isPickup": true, "startTime": "2023-01-14T00:00:00Z", "detour": "0s" }, { "shipmentIndex": 1, "isPickup": true, "startTime": "2023-01-14T00:02:30Z", "detour": "150s" }, { "isPickup": true, "startTime": "2023-01-14T00:05:00Z", "detour": "300s" }, { "startTime": "2023-01-14T00:11:25Z", "detour": "0s" }, { "shipmentIndex": 1, "startTime": "2023-01-14T00:19:29Z", "detour": "503s" }, { "shipmentIndex": 2, "startTime": "2023-01-14T00:29:02Z", "detour": "1324s" } ], "transitions": [ { "travelDuration": "0s", "waitDuration": "0s", "totalDuration": "0s", "startTime": "2023-01-14T00:00:00Z", "routePolyline": {} }, { "travelDuration": "0s", "waitDuration": "0s", "totalDuration": "0s", "startTime": "2023-01-14T00:02:30Z", "routePolyline": {} }, { "travelDuration": "0s", "waitDuration": "0s", "totalDuration": "0s", "startTime": "2023-01-14T00:05:00Z", "routePolyline": {} }, { "travelDuration": "235s", "travelDistanceMeters": 795, "waitDuration": "0s", "totalDuration": "235s", "startTime": "2023-01-14T00:07:30Z", "routePolyline": { "points": "kvteFtfjVAA?C?C@C?A?C@AFMj@s@JKb@k@Zc@LSjA}ARWDGdAxAdAvAXa@@k@AsA\\c@FKp@_A\\c@Ze@fA{ALSFGd@o@rAgBB{BZc@" } }, { "travelDuration": "234s", "travelDistanceMeters": 793, "waitDuration": "0s", "totalDuration": "234s", "startTime": "2023-01-14T00:15:35Z", "routePolyline": { "points": "cwseFti_jVRWj@w@x@eAHLNRHJbApAHLX\\V^?@hA~AT\\PVFFDHDFJNp@~@NRLNNTFFUZIJY^Y^g@p@[`@KP{@fAEFSXe@l@c@h@WZY\\?BELk@v@MNa@l@" } }, { "travelDuration": "323s", "travelDistanceMeters": 1204, "waitDuration": "0s", "totalDuration": "323s", "startTime": "2023-01-14T00:23:39Z", "routePolyline": { "points": "cuseFhjVSTY`@Yb@GHEDIJEF]f@IJi@r@oAbBeCfDKLaApAKNQVIPKPCDQJIBIBM@iAJeALqBVC@C?A?QBYDI@C?_@Dc@FO@a@FDp@HfAHvABVDl@Dj@PpCQDiALsALAQASKwAOgBEe@COCYEa@Es@Eg@" } }, { "travelDuration": "209s", "travelDistanceMeters": 665, "waitDuration": "0s", "totalDuration": "209s", "startTime": "2023-01-14T00:33:12Z", "routePolyline": { "points": "{zteFxbajV?CAYEc@AMC_@AOAK?E?CCWAOAKCe@CY?WScDEm@d@EFA\\ENCB?XEVC^E`@EhBUVCNEB?@?\\Er@IMUe@k@k@w@AAMQa@i@SWQWMQi@u@AC?A" } } ], "routePolyline": { "points": "kvteFtfjVAA?C?C@C?A?C@AFMj@s@JKb@k@Zc@LSjA}ARWDGdAxAdAvAXa@@k@AsA\\c@FKp@_A\\c@Ze@fA{ALSFGd@o@rAgBB{BZc@RWj@w@x@eAHLNRHJbApAHLX\\V^?@hA~AT\\PVFFDHDFJNp@~@NRLNNTFFUZIJY^Y^g@p@[@KP{@fAEFSXe@l@c@h@WZY\\?BELk@v@MNa@l@STY@Yb@GHEDIJEF]f@IJi@r@oAbBeCfDKLaApAKNQVIPKPCDQJIBIBM@iAJeALqBVC@C?A?QBYDI@C?_@Dc@FO@a@FDp@HfAHvABVDl@Dj@PpCQDiALsALAQASKwAOgBEe@COCYEa@Es@Eg@?CAYEc@AMC_@AOAK?E?CCWAOAKCe@CY?WScDEm@d@EFA\\ENCB?XEVC^E`@EhBUVCNEB?@?\\Er@IMUe@k@k@w@AAMQa@i@SWQWMQi@u@AC?A" }, "metrics": { "performedShipmentCount": 3, "travelDuration": "1001s", "waitDuration": "0s", "delayDuration": "0s", "breakDuration": "0s", "visitDuration": "1200s", "totalDuration": "2201s", "travelDistanceMeters": 3457 }, "travelSteps": [ { "duration": "0s", "routePolyline": {} }, { "duration": "0s", "routePolyline": {} }, { "duration": "0s", "routePolyline": {} }, { "duration": "227s", "distanceMeters": 794, "routePolyline": { "points": "kvteFtfjVAA?C?C@C?A?C@AFMj@s@JKb@k@Zc@LSjA}ARWDGdAxAdAvAXa@@k@AsA\\c@FKp@_A\\c@Ze@fA{ALSFGd@o@rAgBB{BZc@" } }, { "duration": "233s", "distanceMeters": 791, "routePolyline": { "points": "cwseFti_jVRWj@w@x@eAHLNRHJbApAHLX\\V^?@hA~AT\\PVFFDHDFJNp@~@NRLNNTFFUZIJY^Y^g@p@[`@KP{@fAEFSXe@l@c@h@WZY\\?BELk@v@MNa@l@" } }, { "duration": "322s", "distanceMeters": 1205, "routePolyline": { "points": "cuseFhjVSTY`@Yb@GHEDIJEF]f@IJi@r@oAbBeCfDKLaApAKNQVIPKPCDQJIBIBM@iAJeALqBVC@C?A?QBYDI@C?_@Dc@FO@a@FDp@HfAHvABVDl@Dj@PpCQDiALsALAQASKwAOgBEe@COCYEa@Es@Eg@" } }, { "duration": "208s", "distanceMeters": 666, "routePolyline": { "points": "{zteFxbajV?CAYEc@AMC_@AOAK?E?CCWAOAKCe@CY?WScDEm@d@EFA\\ENCB?XEVC^E`@EhBUVCNEB?@?\\Er@IMUe@k@k@w@AAMQa@i@SWQWMQi@u@AC?A" } } ], "vehicleDetour": "2201s", "routeCosts": { "model.vehicles.cost_per_hour": 24.455555555555556, "model.vehicles.cost_per_kilometer": 34.57 }, "routeTotalCost": 59.025555555555556 } ], "totalCost": 59.025555555555556, "metrics": { "aggregatedRouteMetrics": { "performedShipmentCount": 3, "travelDuration": "1001s", "waitDuration": "0s", "delayDuration": "0s", "breakDuration": "0s", "visitDuration": "1200s", "totalDuration": "2201s", "travelDistanceMeters": 3457 }, "usedVehicleCount": 1, "earliestVehicleStartTime": "2023-01-14T00:00:00Z", "latestVehicleEndTime": "2023-01-14T00:36:41Z", "totalCost": 59.025555555555556, "costs": { "model.vehicles.cost_per_kilometer": 34.57, "model.vehicles.cost_per_hour": 24.455555555555556 } } }
پاسخ بهینه سازی مسیر شامل یک فیلد routes
سطح بالا است که مسیرهای پیشنهادی را با یک مسیر برای هر وسیله نقلیه نشان می دهد. از آنجایی که درخواست مثال در این راهنما فقط یک وسیله نقلیه را مشخص می کند، routes
شامل یک پیام ShipmentRoute
است.
خواص ShipmentRoute
دو ویژگی مهم برای نوع پیام ShipmentRoute
visits
و transitions
هستند.
هر Visit
نشان دهنده تکمیل یک تحویل یا تحویل از یکی از VisitRequest
های پیام درخواست است. بازدید عملاً کاری است که باید توسط یک وسیله نقلیه در مکان و زمان تکمیل شود.
هر Transition
نشان دهنده وسیله نقلیه ای است که از یک مکان به مکان بعدی حرکت می کند. انتقال می تواند بین یک جفت نقطه شروع خودرو، یک مکان بازدید و نقطه پایان خودرو رخ دهد.
برای بازسازی مسیر کامل وسیله نقلیه، visits
و transitions
ShipmentRoute
باید با هم ترکیب شوند. ترکیب فیلدها در پیشرفت فعالیت خودرو به صورت زیر است:
request.vehicles[0].startLocation -> transitions[0] -> visits[0] ->
transitions[1] -> visits[1] -> transitions[2] -> ... -> visits[3] ->
transitions[4] -> request.vehicles[0].endLocation
یک ShipmentRoute
همیشه یک transitions
بیشتر از visits
دارد، زیرا وسیله نقلیه باید از محل شروع خود تا اولین بازدید خود در ابتدای مسیر و از آخرین بازدید خود تا مکان پایانی خود در انتهای مسیر حرکت کند. اگر وسیله نقلیه فاقد مکان شروع یا پایان باشد، باز هم یک transitions
بیشتر از visits
وجود خواهد داشت زیرا مکان اولین یا آخرین بازدید به ترتیب به عنوان مکان شروع یا پایان وسیله نقلیه استفاده می شود.
در این مثال، سه بازدید از پیکاپ اول دارای انتقال بین آنها با فاصله و مدت زمان صفر هستند زیرا هر سه پیکاپ مکان یکسانی در درخواست دارند.
برای جزئیات بیشتر به مستندات مرجع ShipmentRoute
( REST ، gRPC ) مراجعه کنید.
بهینه سازی ساده سفارش نقطه راه
همانطور که این مثال نشان میدهد، بهینهسازی مسیر بازدیدها را بهعنوان ویژگیهای محمولهها مدل میکند و مفهومی از ایستگاههای بین راهی یا توقفها به عنوان یک موجودیت مستقل ندارد. با این حال، میتوان ایستگاهها یا ایستگاههای بین راهی را بهعنوان محموله با دقیقاً یک VisitRequest
بهعنوان تحویل یا تحویل نشان داد. هنوز باید به وسیله نقلیه یک costPerHour
یا costPerKilometer
اختصاص داده شود تا بهینهساز مسیری بهینه را پیدا کند (برخلاف یافتن هر مسیر ممکن).