Hiểu một thuật toán cho vấn đề trạm xăng


11

Trong vấn đề trạm xăng chúng tôi được cho thành phố { 0 , ... , n - 1 } và đường giữa chúng. Mỗi con đường có chiều dài và mỗi thành phố xác định giá của nhiên liệu. Một đơn vị đường có giá một đơn vị nhiên liệu. Mục tiêu của chúng tôi là đi từ một nguồn đến đích theo cách rẻ nhất có thể. Xe tăng của chúng tôi bị giới hạn bởi một số giá trị.n{0,,n1}

Tôi cố gắng hiểu thuật toán , vì vậy tôi tự viết ra các bước để tính toán giải pháp. Thật không may, tôi đã bị mắc kẹt - tại một số điểm không có cạnh để xem xét, tôi không biết tại sao, có lẽ tôi đang thiếu một cái gì đó.

Ví dụ:
đường:
0 ----------- 1 ------------ 2 -------------- 3
(không phải đơn giản như vậy, nó có thể là bất kỳ biểu đồ nào, tức là có thể có các con đường trong khoảng 0-> 2, 0-> 3, 1-> 3, v.v.)

Nguồn: 0, Đích: 3, Xe tăng: 10 đơn vị
Giá nhiên liệu: 0 : 10 đơn vị, 1 : 10 đơn vị, 2 : 20 đơn vị, 3 : 12 đơn vị
Độ dài: 0-> 1 : 9 đơn vị, 1-> 2 : 1 đơn vị, 2-> 3 : 7 đơn vị
Giải pháp tối ưu: điền 9 đơn vị ở 0 và 8 đơn vị ở 1. Tổng chi phí sau đó là 170 đơn vị (9 * 10 + 8 * 10).

Vì vậy, tôi đã cố gắng tính toán nó như được hiển thị ở đây (đoạn 2.2)

GV[u] is defined as:
GV[u] = { TankCapacity - length[w][u] | w in Cities and fuelPrice[w] < fuelPrice[v] and length[w][u] <= TankCapacity } U {0}

so in my case:
GV[0] = {0}
GV[1] = {0}
GV[2] = {0, 3, 9}
GV[3] = {0}

D(u,g) - minimum cost to get from u to t starting with g units of fuel in tank:
D(t,0) = 0, otherwise:
D(u,g) = min (foreach length[u][v] <= TankCapacity)
         { 
           D(v,0) + (length[u][v] - g) * fuelPrice[u]                             : if  fuelPrice[v] <= fuelPrice[u] and g <= length[u][v]
           D(v, TankCapacity - length[u][v]) + (TankCapacity - g) * fuelPrice[u]  : if  fuelPrice[v] > fuelPrice[u]
         }

so in my case:
D(0,0) = min { D(1,0) + 9*10 }  - D(0,0) should contain minimum cost from 0->3
D(1,0) = min { D(2,9) + 10*10 } - in OPT we should tank here only 8 units :(
D(2,9) = min { ??? - no edges which follows the condition from the reccurence 

Nevertheless D(0,0) = 90 + 100 + smth, so it's already too much.

To achieve the optimal solution algorithm should calculate D(2,7) because the optimal route is:   
(0,0) -> (1,0) -> (2, 7) -> (3, 0) [(v, g): v - city, g - fuel in tank]. 
If we look at G[2] there is no "7", so algorithm doesn't even assume to calculate D(2,7), 
so how can it return optimal solutions?

Tái phát từ tài liệu dường như không hoạt động hoặc nhiều khả năng tôi đã làm gì đó sai.

Ai có thể giúp tôi với điều này?

Câu trả lời:


7

Vấn đề là trong điều kiện cho đối số đầu tiên min()trong phương trình (4) trên p. 7. Hiện tại

c(v) <= c(u) and g < d[u][v]

nhưng nó nên

(c(v) <= c(u) or v = t) and g < d[u][v]

buộc phải đến t để không còn gas. (Cũng như với lời giải thích của tôi dưới đây để biết các lỗi trong Fill-Row (u, q), chúng tôi không bao giờ quan tâm đến chi phí của khí tại t. Và như với đó, một cách khác để khắc phục vấn đề sẽ được ghi đè c (t ) với 0 khi bắt đầu thuật toán.)

Sửa lỗi này (trong thuật toán được xuất bản), kết hợp với việc thêm vào các cạnh bị thiếu như tôi mô tả bên dưới (lỗi của bạn :-P), là đủ để mọi thứ hoạt động.


Một điều bạn còn thiếu là đồ thị G phải hoàn chỉnh (câu đầu tiên của phần 2, trang 4) - và nếu nó chưa hoàn thành, bất kỳ cạnh bị thiếu nào cũng phải được thêm vào, với các trọng số được tìm thấy bằng cách lấy độ dài đường dẫn tối thiểu trong đồ thị. Vì vậy, ví dụ trong biểu đồ ví dụ của bạn, cần có (trong số những người khác) một cạnh từ 1 đến 3 với trọng số 8 (tương ứng với đường dẫn qua 2), để trên thực tế GV [3] = {0, 2}.

Tôi không chắc liệu điều đó sẽ giải quyết hoàn toàn vấn đề cho bạn hay không, nhưng nó sẽ giúp ích.

Một cách riêng biệt, tôi nghĩ rằng có một lỗi trong thuật toán Fill-Row (u, q) trên p. 6: thuật toán này sẽ xử lý trường hợp q = 1 đặc biệt, nhưng không. Tôi tin rằng nó có thể được sửa chữa bằng cách thay đổi

if c(v) <= c(u)

trên dòng 3 đến

if c(v) <= c(u) or q = 1

để buộc bất kỳ chặng cuối cùng đến đích trống. (Theo trực giác, chúng ta nên luôn luôn bỏ qua giá khí ở điểm đến cuối cùng, t.) Một cách khác xung quanh điều này sẽ là ghi đè lên c (t) bằng 0 ngay từ đầu.


q=1c(v)>c(u)

2

Sử dụng giải pháp @j_random_hacker, chúng ta cần chuyển đổi biểu đồ của mình thành một biểu đồ hoàn chỉnh và thay đổi điều kiện từ phương trình (4) sang:

(c(v) <= c(u) or v = t) and g < d[u][v]     

Đồ thị hoàn chỉnh sẽ trông như thế này:

nhập mô tả hình ảnh ở đây

và tính toán cuối cùng:

GV[0] = {0}, GV[1] = {0}, GV[2] = {0, 3, 9}, GV[3] = {0, 2}

D(0,0) = min { D(1,0) + 9 * 10 }
D(1,0) = min { D(2,9) + 10 * 10, D(3,0) + 8*10 }
D(3,0) = 0
... etc

so D(0,0) = 170

Đường dẫn qua 0 -> 1 -> 3 [tổng chi phí 170 $] là giải pháp. Đó là những gì chúng tôi mong đợi :-). Nếu chúng ta cần một tuyến đường, thì chúng ta sẽ có thể chuyển đổi các cạnh bổ sung đó từ giải pháp sang các cạnh đã cho lúc đầu (không nên rất khó khăn).

Tôi chỉ tự hỏi làm thế nào chúng ta nên tránh deadloops trong lần tái phát này. Ví dụ: có thể có deadloop trong khoảng từ 0 <-> 1, vì c (0) <= c (1) và c (1) <= c (0).


Để tham khảo trong tương lai, hãy xem bài đăng meta này :-)
Juho

1

Ý tưởng là để có được nhiên liệu theo yêu cầu ở mức giá rẻ nhất bất cứ nơi nào bạn nhận được (mô hình thuật toán tham lam)

Lấy một số ví dụ. trong ví dụ của bạn

Nguồn: 0, Đích: 3, Xe tăng: 10 đơn vị Giá nhiên liệu: 0: 10 đơn vị, 1: 10 đơn vị, 2: 20 đơn vị, 3: 12 đơn vị Độ dài: 0-> 1: 9 đơn vị, 1-> 2: 1 đơn vị, 2-> 3: 7 đơn vị

Tôi phải đi 9 đơn vị lúc đầu, vì vậy tôi cần đổ đầy bình của mình ở 0 với> = 9 đơn vị (công suất> = 9). Bây giờ, tôi có thể thấy ở mức 1,2,3 tỷ lệ nhiên liệu là> = tỷ lệ nhiên liệu ở mức 0. Vì, tôi muốn mua nhiên liệu cần thiết của mình với mức giá rẻ nhất, tôi sẽ cố gắng đổ đầy 9 + 1 + 7 = 17 đơn vị tại Thành phố 0 thôi. Nhưng, dung tích của xe tăng có thể <17, giả sử 10. Vì vậy, tôi sẽ đổ đầy đến 10. Sau đó, ở 1 tôi có 1 đơn vị nhiên liệu còn lại và tôi phải vượt qua 8 đơn vị nữa, vì vậy, 1 tôi sẽ đổ đầy 7 đơn vị nhiều hơn. Tôi không thể điền vào lúc 2 vì tỷ lệ sẽ cao hơn. Của tôi, tổng chi phí = 10 * 10 + 7 * 10 = 170.

Cidijij

i) đầy đủ = 0

i=0n1liCi>Clll=n1dllk=i+1ldk,k+1d l - i phút d l - i = lmindlđầy đủ, công suất} nhiên liệu đơn vị tại thành phố . đầy đủ = { đầy đủ, dung lượng}. Đặt .imindli=l


Cảm ơn về câu trả lời của bạn! Thật không may, tôi đã không xác định rõ ràng đủ. Bạn giả sử, biểu đồ đó sẽ đơn giản như ví dụ của tôi, nhưng nó có thể là bất kỳ biểu đồ nào, tức là cũng có thể có các đường 0-> 2, 1-> 3, v.v.
Wojciech Kulik

Ya, như bạn đã không đề cập rằng trước khi tôi giả định tất cả các thành phố được kết nối theo kiểu tuyến tính (biểu đồ là một đường dẫn đơn giản).
Sayan Bandyapadhyay
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.