본문 바로가기

카테고리 없음

Shortest Path without weight

Native Graph 구조로 이미 데이터가 연결되어 있다는 것은

어떤 효과를 가져 오는가 ? 

 

아닌것을 아닌것으로, 없는 연결을 없는 것으로 확정하는데 리소스가 별로 들지 않는다

특정 조건에 해당하는 값이 없는 경우에서 무언가를 없다라고 확인하려면 전수 조사가 들어가야 했다면

 

그래프 에서는 적어도 자신과 연결된 것을 빠르게 확인하고 판정을 할 수 가 있다 

도달이 안되면 없는 것이다

전체를 찾는 형태가 아니라 그 출발점이 없으면 출발 자체를 못하기에 바로 확인이 된다. 

연결도 연결이 안되어 있으면 관련 없는 모든 것을 찾은 다음에 없다가 아니라, 자신과 연결된 것에서 찾으면서 없으면 없다이다. 

 

스키마가 설계된 상태에서 

 

 - Tree 를 누구로 부터 시작할지만 알면 된다 (물론 내부적으로 어떤 vertex 와 edge 가 있는지 input 은 필요하다)
 - RDB 는 스키마를 알고 있는 것 뿐만 아니라 데이터를 어떻게 연결할지 데이터베이스 테이블 설계를 이해하고 

   복잡한 조인 쿼리를 짜야 하는데 이도 효과적으로 성능 효율적으로 짜야한다. 더하여 제대로 되니 인덱스 설계가 안되어 있다면 몇차례의 조인을 걸치면서 급격히 성능이 느려지거나 특별히 1:N 그리고 N:1:N 형태의 조인이 엮여질 때는 급격한 부하 증가로 쿼리가 응답을 주지 못하는 경우도 발생할 수 있다. 

 

 

Let's think a bit deeper dive.

 

CREATE QUERY tg_shortest_ss_no_wt (VERTEX source, SET<STRING> v_type, SET<STRING> e_type, 
  INT output_limit = -1, BOOL print_accum =TRUE, STRING result_attr ="", STRING file_path ="",
  BOOL display_edges =FALSE) {
/*
Single-source shortest path algorithm, with unweighted edges.
From the source vertex, finds the unweighted shortest path (number of hops, INT value)
 source: start vertex                         print_accum: print JSON output
 v_type: vertex types to traverse             result_attr: INT attr to store results to
 e_type: edge types to traverse               file_path: file to write CSV output to
 output_limit: max #vertices to output        display_edges: output edges for visualization
*/

FILE f(file_path);
MinAccum<INT> @dis;
OrAccum @visited;
ListAccum<VERTEX> @path;
SetAccum<EDGE> @@edgeSet;

##### Initialization  #####
Source = {source};
Source = SELECT s 
 FROM Source:s
 ACCUM s.@visited += true, 
   s.@dis = 0,
   s.@path = s; 
ResultSet = {source};

##### Calculate distances and paths #####
WHILE(Source.size()>0) DO
Source = SELECT t
 FROM Source:s -(e_type:e)-> v_type:t
 WHERE t.@visited == false
 ACCUM t.@dis += s.@dis + 1,
   t.@path = s.@path + [t],
   t.@visited += true
ORDER BY getvid(t);
ResultSet = ResultSet UNION Source;
END;

IF file_path != "" THEN
f.println("Vertex_ID","Distance","Shortest_Path");
END;

ResultSet = SELECT s FROM ResultSet:s 
POST-ACCUM 
IF result_attr != "" THEN s.setAttr(result_attr, s.@dis) END,
IF file_path != "" THEN f.println(s, s.@dis, s.@path) END
;


IF print_accum THEN
    IF output_limit >= 0 THEN
        ResultSet = SELECT s FROM ResultSet:s LIMIT output_limit;
    END;
PRINT ResultSet[ResultSet.@dis, ResultSet.@path];
IF display_edges THEN

ResultSet = SELECT s FROM ResultSet:s -(e_type:e)-> v_type:t
ACCUM @@edgeSet += e;
PRINT @@edgeSet;
END;
END;
}

 

 

다음과 같은 형태로 실행함 (little toy with dummy data)

GSQL > run query tg_shortest_ss_no_wt(("jacob", "vperson"), ["vperson", "vpersont","vpersontt", "vperson4"], ["eisafriend1","eisafriend23" ], 3, TRUE, "", "", FALSE)

 

 

file output (jacob 을 출발점으로 갈 수 있는 경로들의 거리 Distance 와 Path