2014-01-14 3 views
0

SQL 서버 테이블에 URL 리디렉션 테이블이 있으며 리디렉션마다 ID, FromURL 및 ToURL 필드가 있습니다.리디렉션 체인의 시작과 끝 찾기

사용자가 여러 번이 아닌 한 번만 리디렉션되도록 단일 리디렉션으로 대체 할 수 있도록 표에서 일련의 리디렉션이있는 곳을 찾아야합니다.

테이블의 예는 다음과 같습니다

Sample Table

당신이 볼 수 있듯이, 사용자가 방문의 URL A는, 그들이 B로 리디렉션됩니다 있다면, B에서 C로 다음 C에서 D로 페이지로드 속도를 높이기 위해 A에서 D로 단일 리디렉션으로 바꾸고 싶습니다.

SELECT r.ID , 
     r.FromURL , 
     r.ToURL 
FROM dbo.redirect r 
WHERE fromURL NOT IN (SELECT ToURL 
         FROM dbo.redirect r2) 
다음 각 체인의 시작을 찾을 수

은 내가 재귀 CTE와 커서없이이 작업을 수행 할 수있을 거라고 생각하지만이 완전히 붙어있어, 최고의 내가 관리 하였다

이렇게하면 FromURL이 다른 리디렉션에 의해 리디렉션되지 않은 레코드를 선택하여 체인 (또는 체인에없는 체인)의 시작을 알 수 있습니다. 재귀 CTE 예제를 통해 다음을 시도해 보았을 때, 결국 정크 데이터 나 재귀 한계가 발생했습니다. 당신이 볼 수 있듯이

Ideal result

, 리디렉션의 사슬이 하나 하나로 대체되었습니다, 그래서 모든 :

이상적으로이 나가 싶은 무엇을 다음과 같은 데이터는 레벨의 계층 구조는 이제 체인의 끝으로 직접 이동합니다.

나는 우리 웹 팀을 위해 뭔가를하기로 동의 한 DBA 일 뿐이며, 이제는 누군가가 나를 도와 줄 수 있다면 T-SQL에 대한 나의 능력을 완전히 잃어 버렸습니다.

+0

당신은 테이블을 풀다운 수 있으며 다른 언어로합니까? –

+0

그래, 내가 왜 다른 언어로하기가 더 쉽다면 나는 보지 않는다. 나는 그것을 보아서 기쁘다. 내가 익히 알고있는 유일한 언어는 C#이다. (주로 SQL CLR을 사용한다. 프로 시저),하지만 난 항상 뭔가 새로운 것을 시도하고 싶어 :-) – steoleary

+0

당신은 C#을 사용하고 유향 그래프를 만들 수 있습니다. 그럼 당신은 연결이 끊어진 선으로 끝날 것이라고 생각합니다. 그것들을 가리 키지 않는 모든 노드를 찾아서 각 라인을 압축하여 처음에 모든 중간 노드를 저장하십시오. 이것은 당신이 메모리에 남아 있거나 재빨리 접근 할 수 있기 때문에 그것을 재 계산할 필요가 없다고 가정합니다. –

답변

1

일반적인 해결 방법은 "Directed Acyclic Graph", "Traversal", "SQL"을 검색하는 것입니다. hansolav.net/sql/graphs.html#topologicalsorting 좋은 정보 있습니다.

빠른 답변이 필요한 경우 여기를 클릭하십시오. 효율적이지 않고 비순환 적 입력이 필요하지만 SQL에 익숙하지 않은 사람은 읽을 수 있습니다. 재귀 CTE와 또는

SELECT id, FromUrl, ToUrl 
INTO #temp 
FROM dbo.redirect 

WHILE @@ROWCOUNT > 0 
BEGIN 
    UPDATE cur 
    SET ToUrl = nxt.ToURL 
    FROM #temp cur 
    INNER JOIN #temp nxt ON (cur.ToURL = nxt.FromURL) 
END 

SELECT * FROM #temp 

:

;WITH cte AS (
    SELECT 1 as redirect_count, id, FromURL, ToUrl 
    FROM dbo.redirect 
    UNION ALL 
    SELECT redirect_count + 1, cur.id, cur.FromURL, nxt.ToURL 
    FROM cte cur 
    INNER JOIN @t nxt ON (cur.ToURL = nxt.FromURL) 
) 
SELECT 
    t1.id, t2.FromUrl, t2.ToUrl 
FROM dbo.redirect t1 
CROSS APPLY (
    SELECT TOP 1 FromUrl, ToUrl 
    FROM cte 
    WHERE id = t1.id 
    ORDER BY redirect_count DESC 
) t2 
+0

그 링크에 대한 환호가 정말 흥미롭고 유용하게 보입니다. 내일 그 질문과 쿼리를 살펴보고 어떻게 시작하는지 알려 드리겠습니다. – steoleary

관련 문제