답변:
이것이 바로 pgRouting에서 shortest_path (Dijkstra의 알고리즘)의 작동 방식입니다. 소스와 대상이 동일한 두 개의 모서리가있는 경우 임의의 것 (정확히 말하면 데이터베이스에서 나온 것)이 사용됩니다. 나는 그에 대한 해결책을 모르지만 몇 가지 해결 방법이 있습니다.
가능하면 해당 가장자리 중 하나를 두 개로 나눠야합니다. 나는 그것을 테스트하지는 않았지만 그 행동을 고쳐야합니다.
데이터 세트를 수정할 수없는 경우를위한 다른 솔루션입니다. 테이블에 'shorter_alternative'필드를 추가하십시오. 샘플 쿼리는 필요에 따라 수정하십시오. 아이디어가 설명되기를 바랍니다.
UPDATE roads t1
SET shorter_alternative = t2.id
FROM roads t2
WHERE
((t2.source = t1.source AND t2.target = t1.target) OR
(t2.source = t1.target AND t2.target = t1.source)) AND
(t2.length < t1.length)
이제 모서리 '0.098'에는 모서리 '0.011'의 id가 포함됩니다. shorter_alternative 필드에서 다른 모든 모서리는 null입니다. shortest_path 조회를 작성한 후 리턴 된 데이터 세트를 점검하십시오. shorter_alternative 필드 세트가있는 행이 있으면 변경하십시오.
문제는 이미 이전 답변에서 설명되었습니다. "vertex-based"최단 경로 알고리즘의 문제로, 소스와 대상 만 신경 쓰는 것입니다.
이슈 트래커에서 티켓 및 알고리즘 구현 변경 가능한 솔루션이 있습니다 : https://github.com/pgRouting/pgrouting/issues/34을 (사람이 밖으로 시도하고 끌어 오기 요청을 보낼 수 있다면 좋겠지은 - )
또 다른 가능성은 앞에서 언급 한대로 "병렬 도로 링크"를 분할하는 것입니다. 또는 에지에서 에지로 라우팅되는 Shooting Star 알고리즘을 사용하여 두 도로 링크를 모두 "알 수 있습니다".
또는 비용으로 도로 네트워크를 주문한 다음 소스와 대상의 고유 한 조합 만 선택할 수 있습니다.
SELECT * FROM shortest_path(
'SELECT DISTINCT ON (source, target)
gid as id,
source::integer,
target::integer,
cost::double precision
FROM ways ORDER BY source, target, cost',
true,false
);
이것은 가장 저렴한 경로를 검색한다고 가정합니다. 그렇지 않으면 ORDER BY ... DESC
.
이것이 성능에 영향을 미치는지 확인해야합니다.
실제로 pgRouting에 대한 패치를 만들었습니다.이 문제를 해결합니다 : https://github.com/pgRouting/pgrouting/issues/78