SQL Server 2008-분할 및 클러스터형 인덱스


16

DB 설계를 완전히 제어 할 수 없다고 말 함으로써 현재 시스템의 여러 측면 을이 시나리오의 목적으로 변경할 수는 없습니다 .

디자인 측면을 다시 생각해야하는 방법에 대한 의견은 정확하지만 도움이되지 않습니다. :)

약 150 필드 너비와 약 600m 행의 매우 큰 테이블이있어 많은 수의 프로세스를 구동합니다. 이는 데이터웨어 하우스 상황에 있으므로 예약 된로드 프로세스 외부에 업데이트 / 삽입이 없으므로 색인이 많이 생성됩니다.

이 테이블의 파티셔닝을 시도했으며 파티션 된 테이블의 인덱싱에 대한 일부 우려가 있습니다. 파티셔닝에 대한 경험이 없으므로 입력 또는 링크에 감사드립니다. BOL 또는 msdn에서 내가 찾은 것을 구체적으로 찾을 수 없습니다.

현재 우리는 전화 IncidentKey할 필드를 클러스터링합니다.이 필드는 varchar(50)독특하지 않습니다. 1 ~ 100 개의 레코드를 동일하게 가질 수 있습니다 IK(의견은 없습니다). 우리는 종종 오래된 IncidentKey레코드 에 대한 새로운 데이터를 얻으 므로 순차적이 아닙니다.

IncidentDate파티션이 올바르게 작동하려면 클러스터 된 인덱스 키에 파티션 필드를 포함시켜야한다는 것을 알고 있습니다. 나는 그것이 될 것이라고 생각합니다 IncidentKey, IncidentDate.

문제는 "새"파티션의 레코드가 클러스터 된 인덱스의 "오래된"파티션의 레코드보다 앞에 있어야하는 경우 클러스터 된 인덱스의 메커니즘이 파티션 된 테이블의 2 개 부분 키에서 어떻게 작동 하는가입니다.

예를 들어 5 개의 레코드가 있습니다.

IncidentKey    Date

ABC123        1/1/2010
ABC123        7/1/2010
ABC123        1/1/2011
XYZ999        1/1/2010
XYZ999        7/1/2010

새 레코드를 얻는 경우 ABC123, 2/1/2011클러스터 된 인덱스 BEFORE 에 있어야합니다 XYZ999, 1/1/2010. 어떻게 작동합니까?

조각화와 포인터를 가정하고 있지만 이중 부분 키가있는 분할 된 테이블에서 분할되지 않은 클러스터형 인덱스의 물리적 저장소 및 구성에 대한 정보를 찾을 수 없습니다.


테이블을 분할하기로 결정한 이유는 무엇입니까? 파티셔닝의 이점은 무엇입니까?
Remus Rusanu

@Remus-실제로 테스트로하고 있으므로 파티션이 하나 있고 파티션되지 않은 버전이 하나 있습니다. 예상되는 이점은로드 시간과 인덱스 빌드 시간이 단축된다는 것입니다. 우리는 매주 약 1 주일 정도 걸리는 ETL 작업을 수행하므로 시간이 크게 단축되기를 바랍니다. 또한 약 3TB를 배포하여이를 줄이려고합니다.
JNK

답변:


18

분할 된 테이블은 실제로 서로 연결된 개별 테이블의 모음과 비슷합니다. 따라서 by by IncidentKey및 partition by IncidentDate의 예에서, 파티셔닝 함수는 테이블을 두 개의 파티션으로 분할하여 1/1/2010이 파티션 1에 있고 7/1/2010이 파티션 2라고 가정합니다. 데이터는 다음과 같이 디스크에 배치됩니다.

Partition 1:
IncidentKey    Date
ABC123        1/1/2010
ABC123        1/1/2011
XYZ999        1/1/2010

Partition 2:
IncidentKey    Date
ABC123        7/1/2010
XYZ999        7/1/2010

낮은 수준에는 실제로 두 개의 고유 한 행 집합이 있습니다. 모든 행 집합을 하나로 검색, 검색 및 업데이트하는 계획을 만들어 단일 테이블의 환영을주는 쿼리 프로세서입니다 .

비 클러스터형 인덱스의 모든 행에는 해당하는 클러스터형 인덱스 키가 있습니다 (예 :) ABC123,7/1/2010. 클러스터형 인덱스 키에는 항상 파티셔닝 키 열이 포함되므로 엔진은이 값 (이 경우 파티션 2)을 검색하기 위해 클러스터형 인덱스의 어떤 파티션 (행 세트)을 항상 알고 있습니다.

이제 파티셔닝을 처리 할 때마다 NC 인덱스가 정렬되는지 (NC 인덱스가 클러스터 된 인덱스와 정확히 동일하게 파티션 됨) 또는 정렬되지 않은지 (NC 인덱스가 파티션되지 않았거나 클러스터 된 인덱스와 다르게 파티션 됨)를 고려해야합니다. . 정렬되지 않은 인덱스는 더 유연하지만 몇 가지 단점이 있습니다.

정렬 된 인덱스를 사용하면 이러한 문제가 해결되지만 물리적, 스토리지 설계 옵션이 데이터 모델에 파급되기 때문에 자체적 인 문제가 발생합니다.

  • 정렬 된 인덱스는 고유 제한을 더 이상 생성 / 강제 할 수 없음을 의미합니다 (파티션 열 제외).
  • 분할 된 테이블을 참조하는 모든 외래 키는 관계형으로 분할 키를 포함해야합니다 (파티션 키는 정렬 때문에 모든 인덱스 에 있기 때문에 ). 따라서 분할 된 테이블을 참조하는 모든 테이블에는 분할 키 열 값이 포함되어야합니다. Orders-> OrderDetails를 생각하십시오. Orders에 OrderID는 있지만 OrderDate로 분할 된 경우 , 외래 키 제한 조건을 올바르게 선언하려면 OrderDetails에 OrderID뿐만 아니라 OrderDate 포함되어야합니다 .

내가 찾은 이러한 효과는 파티셔닝을 배포하는 프로젝트를 시작할 때 거의 언급되지 않았지만 존재하며 심각한 결과를 초래합니다.

정렬 된 인덱스가 드물거나 극단적 인 경우에는 다음을 고려하십시오. 많은 경우 ETL 및 파티셔닝 솔루션의 초석은 스테이징 테이블의 빠른 전환입니다. 스위치 인 작업에는 정렬 된 인덱스가 필요합니다.

아, 한 가지 더 : 외래 키에 대한 나의 모든 주장과 다른 테이블에 파티션 열 값을 추가하는 파급 효과는 조인 에도 동일하게 적용됩니다 .


완벽하게, 이것이 바로 내가 찾던 것입니다. 우리는 스와핑이 우리가하고 싶은 일에 대한 추첨의 일부 인 정렬 된 인덱스를 사용해야합니다. 우리는 또한 해당 IncidentKey필드 에 대해 총계 함수 그룹을 작성 하는데, 이것이 심각하게 방해가 될 것이라고 생각합니다. 모든 세부 사항에 감사드립니다!
JNK

일반적으로 파티션 전환 작업의 이점은 모든 문제보다 중요합니다.
Remus Rusanu

그것이 우리의 희망입니다, 우리는 곧 보게 될 것입니다!
JNK

9

클러스터형 인덱스에 여러 파티션이있는 경우 각 파티션에는 해당 특정 파티션에 대한 데이터가 포함 된 B- 트리 구조가 있습니다. 예를 들어, 클러스터형 인덱스에 네 개의 파티션이 있으면 네 개의 B- 트리 구조가 있습니다. 각 파티션에서 하나씩. 참조 클러스터형 인덱스 구조

분할 된 인덱스에 대한 특별 지침

파티션 된 인덱스의 특정 파티션을 재 빌드 할 수 있습니다.

예 :

ALTER INDEX IX_TransactionHistory_TransactionDate
ON Production.TransactionHistory
REBUILD Partition = 5;
GO

+1 링크에 대해서는 특별 지침을 읽었지만 그 단락을 놓쳤습니다. 후속 질문-우리는 IncidentKey현장에서 많은 집계를 수행하는데 이것이 성능에 부정적인 영향을 줄 것이라고 생각합니까?
JNK

특정 상황을 모두 알지는 못하지만 IncidentDate로 파티셔닝하는 것이 더 나을 수도 있습니다.
Mitch Wheat

우리는 날짜에 분할하고 있지만 클러스터 된 키가 켜져 있습니다 IncidentKey. 우리는 이것에 대해 많은 조인을하고 있으며 그것을 클러스터링하는 데 일종의 제도적 일입니다. 대체 키를 테스트하고 있지만 지금은 이것이 사용해야합니다.
JNK
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.