복붙노트

[SQL] 나는 VARCHAR 또는 INT의 기본 키가있는 테이블을 설계해야 하는가?

SQL

나는 VARCHAR 또는 INT의 기본 키가있는 테이블을 설계해야 하는가?

나는이 주관적이다 알지만, 사람들의 의견과 SQL 서버 테이블 구조를 설계 할 때 적용 할 수 있다는 희망 몇 가지 모범 사례를 알고 싶습니다.

나는 개인적으로 그것은 또한 외래 키로이 사용하는 다른 테이블에서 동일한 고정 된 길이를 전달 될 필요가 의미하기 때문에 고정 (최대) 길이 VARCHAR에 테이블을 키 입력하면, 노 더 없음을 느낀다. 즉, 인간의 실수가 발생할 수 밖에 없다 보드에 걸쳐 동일한 길이를 적용 할 필요가 없도록, 테이블 1 int를 것 사용 VARCHAR (10), 다른 VARCHAR (20)을 갖는다.

테이블의 유지이 초기 설정에 악몽 같은 소리, 플러스 수단의 미래는 너무 복잡합니다. 예를 들어, 키 입력 VARCHAR 컬럼이 갑자기 이제 가서 선 아래로 거대한 작업 년이 될 수있는 다른 모든 테이블을 업데이트해야 12 개 문자 대신 10이됩니다 말한다.

내가 잘못? 내가 여기서 뭔가를 놓친 적이 있습니까? 나는 다른 사람이 생각하고 기본 키에 대한 INT 고수 경우 피하기 유지 보수 악몽에 가장 좋은 방법은 무엇인지 알고 싶습니다.

해결법

  1. ==============================

    1.나는 확실히 각 테이블에 INT NOT NULL IDENTITY (1,1) 필드를 사용하는 것이 좋습니다 것입니다 기본 키.

    나는 확실히 각 테이블에 INT NOT NULL IDENTITY (1,1) 필드를 사용하는 것이 좋습니다 것입니다 기본 키.

    신원 필드를 사용하면 데이터베이스 핸들을 모두 확인 정말 독특한 모두,보다 쉽게하고 기본에 사용하는 것이 더 적합입니다 있도록 INT 데이터 형, 그냥 4 바이트, 고정입니다 만드는 세부 사항 (및 클러스터링을하도록 할 수 있습니다 테이블에서) 키를 누릅니다.

    그리고 맞아요은 - INT는 INT는 INT입니다 - 당신이 이제까지 재 작성을 이동 및 / 또는 외래 키 관계를 업데이트 할 필요가 없습니다 있도록 그것은 아무것도의 크기를 변경하지 않습니다.

    (10) 또는 (20) 대신 4 바이트, 그리고 사람들이 많이 모르는 것 - - 클러스터링 키 값마다의 모든 단일 인덱스 항목을 반복하는 VARCHAR (10) 또는 (20)를 사용하여 너무 많은 공간을 사용 (- 저렴 -뿐만 아니라 SQL 서버의 메인 메모리에 그냥 디스크에) 하나 때문에 잠재적으로, 당신은 공간을 많이 낭비하고, 테이블에 인덱스를 비는 클러스터. 그것의 변수 (4 수도 20 개 문자 수 있습니다) 어렵게 SQL 서버에이기 때문에 또한, 제대로 좋은 인덱스 구조를 유지.

    즙을 짜고 난 찌꺼기

  2. ==============================

    2.기본 키를 선택할 때하는 데는 보통 당신은 또한 클러스터 키를 선택합니다. 그들 둘은 종종 혼동되지만 차이를 이해한다.

    기본 키를 선택할 때하는 데는 보통 당신은 또한 클러스터 키를 선택합니다. 그들 둘은 종종 혼동되지만 차이를 이해한다.

    기본 키는 논리적 비즈니스 요소입니다. 기본 키는 개체를 식별하기 위해 응용 프로그램에서 사용되며, 기본 키에 대한 논의는 자연 키 또는 대용 키를 사용하는 대부분 거세한 숫양이다. 링크는 더 많은 세부 사항으로 이동하지만, 기본적인 아이디어는 대리 키가 더 비즈니스 엔티티와 관련하여 어떠한 의미가없는 동안 자연 키 ID 또는 ROWID처럼, 사회 보장 번호 (SSN) 또는 전화 번호와 같은 기존 개체 속성에서 파생 된 것입니다 그리고 그들은이다 보통 형 IDENTITY 또는 UUID 어떤 종류의. 내 개인적인 의견은 대리 키가 자연 키에 뛰어난 것을, 그리고 선택 지역 만 applicaitons, 분산 된 데이터의 모든 종류에 대한 GUID의 항상 ID 값이어야한다. 기본 키는 결코 개체의 수명 동안 변경되지 않습니다.

    클러스터 키는 테이블의 행의 물리적 스토리지를 정의하는 열쇠입니다. 대부분의 시간은 기본 키 (논리적 개체 식별자)와 중복 있지만 실제로 시행도 필요하지 않습니다. 두 사람이 서로 다른 경우는 테이블 구현이 기본 키에 클러스터되지 않은 고유 인덱스가 의미합니다. 클러스터링 키 값 actualy 물리적 새로운 위치로 이동되는 테이블의 행의 결과, 행의 수명 동안 변경 될 수있다. 당신이 좋은 클러스터 키를 선택, 클러스터 키에서 기본 키를 분리 (때로는 당신이)해야하는 경우 훨씬 더 열심히 기본 키를 선택보다. 클러스터 된 키 디자인을 구동 두 가지 기본 요소가 있습니다 :

    데이터 액세스 패턴. 이 I에 의해 테이블이 쿼리 및 업데이트되는 방식을 이해합니다. 클러스터 키가 테이블의 행의 실제 순서를 결정하는 것을 기억하십시오. 특정 액세스 패턴의 경우, 일부 레이아웃은 쿼리 속도 또는 업데이트 concurency와 관련하여 세상의 모든 차이를 만들 :

    저장 고려 사항. 클러스터 된 키 폭은 테이블의 저장에 큰 repercursions있다. 큰 키가 더 많은 공간을 차지할 수 있도록 하나의 키는 B- 트리의 모든 비 리프 페이지에서 공간을 차지합니다. 둘째, 종종 더 중요한, 모든 비 클러스터 키는 각 행의 클러스터 키의 전체 폭을 저장해야합니다 있도록 클러스터 키가 아닌 모든 clustred 키에 의해 조회 키로 사용한다는 것입니다. 이 VARCHAR (256)와 같은 대형 클러스터 키를 만들고 클러스터 된 인덱스 키에 대한 빈약 한 선택을 GUID를 것입니다. 또한 키의 선택은 때때로 크게 성능에 영향을 미치는, 클러스터 된 인덱스 조각화에 영향을 미친다.

    이 두 힘은 때로는 대립 될 수 저장 문제를 일으킬 특정 대형 클러스터 키를 필요로하는 데이터 액세스 패턴. 물론 이러한 경우에 균형이 필요하지만 마법의 공식은 존재하지 않는다. 당신은 측정하고 당신은 스위트 스폿 (sweet spot)에 도착 테스트합니다.

    그래서 우리는이 모든에서 무엇을해야합니까? 항상 또한 양식 ENTITY_ID의 IDENTITY (1,1) NOT NULL의 기본 키 클러스터 키를 고려로 시작합니다. 두 개의 별개 따라 테이블을 구성 (예를 들어 날짜별로. 파티션) 때 appropiate.

  3. ==============================

    3.나는 필드 유형이 대부분 "정상"데이터베이스 설계에서 최선의 선택을 위해 일반 정보 INT (또는 정체성)에 그 동의 것입니다 :

    나는 필드 유형이 대부분 "정상"데이터베이스 설계에서 최선의 선택을 위해 일반 정보 INT (또는 정체성)에 그 동의 것입니다 :

    즉 당신은 또한 데이터를 알 필요가 말했다. 당신이 부호있는 32 비트 INT를 날려 버릴려고하는 경우에, 당신은 서명에 대해 생각해야합니다. 해당 통해 타격에 갈 경우, 아마도 64 비트의 int 당신이 원하는 무엇인가. 아니면 당신은 쉽게 데이터베이스 인스턴스 / 파편 사이에 동기화 확인하기 위해 UUID / 해시가 필요합니다.

    불행하게도, 그것은 따라 달라 YMMV하지만 당신이하지에 좋은 이유가없는 한 나는 확실히 INT / ID를 사용하십시오.

  4. ==============================

    4.당신이 말했듯이, 일관성이 핵심입니다. 나는 개인적으로 부호의 int를 사용합니다. 당신은 당신이 데이터의 우스꽝스러운 양의 작업을하지 않는 한 그들 부족하지 않을거야, 당신은 항상 키 열 필요가 유형으로 알 수 있으며, 개별 열에 대한 올바른 값을 찾고 갈 필요가 없습니다.

    당신이 말했듯이, 일관성이 핵심입니다. 나는 개인적으로 부호의 int를 사용합니다. 당신은 당신이 데이터의 우스꽝스러운 양의 작업을하지 않는 한 그들 부족하지 않을거야, 당신은 항상 키 열 필요가 유형으로 알 수 있으며, 개별 열에 대한 올바른 값을 찾고 갈 필요가 없습니다.

  5. ==============================

    5.이 운동을 통해 수많은 시간을 진행 한 후 결과에 시스템을 지원을 바탕으로, INT는 항상 더 나은 것을 담요 문에 몇 가지주의 사항이 있습니다. 이유가없는 한 일반적으로, 나는 그와 함께 갈 것입니다. 그러나, 참호에서, 여기에 몇 가지 장점과 단점이 있습니다.

    이 운동을 통해 수많은 시간을 진행 한 후 결과에 시스템을 지원을 바탕으로, INT는 항상 더 나은 것을 담요 문에 몇 가지주의 사항이 있습니다. 이유가없는 한 일반적으로, 나는 그와 함께 갈 것입니다. 그러나, 참호에서, 여기에 몇 가지 장점과 단점이 있습니다.

    INT

    GUID

  6. ==============================

    6.최적의 성능을 위해, 시간의 99.999 %가 기본 키는 하나의 정수 필드해야한다.

    최적의 성능을 위해, 시간의 99.999 %가 기본 키는 하나의 정수 필드해야한다.

    당신은 기본 키를 필요로하지 않는 데이터베이스 또는 여러 데이터베이스에서 여러 테이블에서 고유해야합니다. 나는이 질문이 태그 된 방법이기 때문에 당신이 MS SQL-Server에 대한 요구된다고 가정하고있다. 이 경우, 대신 GUID 필드를 사용하는 것이 좋습니다. 포함 된 VARCHAR보다 더 있지만, GUID 필드 성능은 정수로 좋은으로하지 않습니다.

  7. ==============================

    7.사용 INT. 귀하의 포인트는 모두 유효합니다; I는 다음과 같이 우선 순위 것입니다 :

    사용 INT. 귀하의 포인트는 모두 유효합니다; I는 다음과 같이 우선 순위 것입니다 :

    1 & 2는 개발자의 시간 / 에너지 / 노력을 필요로한다. 3 & 4가에 하드웨어를 던질 수 있습니다.

  8. ==============================

    8.조 셀코 여기에 있었다면, 그는 ... 야단있을 것입니다 ;-)

    조 셀코 여기에 있었다면, 그는 ... 야단있을 것입니다 ;-)

    나는 단단하고 빠른 규칙 등의 INT는 항상 적절하지 않은 것을 지적하고 싶다. 당신이 지금 등, 자동차, 트럭의 모든 종류의 차량 테이블이 당신이 VehicleType 테이블을했다라고 말한다. 모든 트럭을 얻기 위해 원하는 경우에 당신은 (AN INT 정체성 씨앗)이 작업을 수행 할 수 있습니다 :

    SELECT V.Make, V.Model
    FROM Vehicle as V
    INNER JOIN VehicleType as VT
    ON V.VehicleTypeID = VT.VehicleTypeID
    WHERE VT.VehicleTypeName = 'Truck'
    

    이제 VehicleType에 대 Varchar PK와 :

    SELECT Make, Model
    FROM Vehicle 
    WHERE VehicleTypeName = 'Truck'
    

    코드는 조금 깨끗하고 당신은 가입하지 마십시오. 아마도 조인 세상의 끝이 아니다, 그러나 당신은 당신의 도구 상자에서 하나의 도구가 있다면, 당신은 성능 향상 및 청소기 스키마에 대한 몇 가지 기회를 놓치고있어.

    그냥 생각했다. :-)

  9. ==============================

    9.INT는 일반적으로 권장되는 동안, 정말 상황에 따라 달라집니다.

    INT는 일반적으로 권장되는 동안, 정말 상황에 따라 달라집니다.

    당신은 유지 보수와 관련있는 경우, 다른 유형은 가능과 같습니다. 예를 들어, 기본 키로 매우 효과적으로 GUID를 사용할 수 있습니다. 이이 일을하지 않는 이유는, 그러나 일관성은 그들 중 하나가 아닙니다.

    당신이하지에 좋은 이유가 없다면 그러나 예, int로는 사용하기 간단하고는 가장 가능성이 당신에게 어떤 문제가 발생할 수 있습니다.

  10. ==============================

    10.PostgreSQL의 I은 일반적으로 기본 키를 생성하기위한 "직렬"또는 "BIGSERIAL" '데이터 유형'을 이용하여. 값은 자동 증가하고 나는 항상 쉽게 작업 할 정수를 찾을 수 있습니다. 그들은 본질적으로 "AUTO_INCREMENT"로 설정되어 MySQL의 정수 필드에 해당합니다.

    PostgreSQL의 I은 일반적으로 기본 키를 생성하기위한 "직렬"또는 "BIGSERIAL" '데이터 유형'을 이용하여. 값은 자동 증가하고 나는 항상 쉽게 작업 할 정수를 찾을 수 있습니다. 그들은 본질적으로 "AUTO_INCREMENT"로 설정되어 MySQL의 정수 필드에 해당합니다.

  11. ==============================

    11.하나는 32 비트 범위는 당신이 무슨 일을하는지에 대한 충분한인지에 대해 열심히 생각해야한다. 트위터의 상태 ID는 32 비트의 INT했다 그들은 뛰쳐 때 문제가 있었다.

    하나는 32 비트 범위는 당신이 무슨 일을하는지에 대한 충분한인지에 대해 열심히 생각해야한다. 트위터의 상태 ID는 32 비트의 INT했다 그들은 뛰쳐 때 문제가 있었다.

    여부는 논쟁의 여지가있는 BIGINT 또는 그 상황에서 UUID / GUID를 사용하고 난 하드 코어 데이터베이스 사람이 아니지만, UUID를 사용하면 필드 크기를 변경해야한다는 걱정없이 고정 길이 VARCHAR에 저장할 수 있습니다.

  12. ==============================

    12.우리는 테이블의 기본 키는 "비즈니스 로직을"이없는 것을 명심해야하고 그것이 속해있는 기록의 식별해야합니다. 이 간단한 규칙의 int 특히 신원 INT 따르는 것은 매우 좋은 솔루션입니다. VARCHAR에 대해 물어 난 당신이 "사람"테이블에 키로서, 예를 들어 "전체 이름"을 사용하여 의미 있다고 생각한다. 그러나 우리는 "조지 A. 뭔가"에서 "조지 뭔가"에서 이름을 변경하려면 어떻게해야할까요? 그리고 필드는 어떤 크기가 될 것인가? 우리가 크기를 변경하는 경우 우리는 너무 모든 해외 테이블의 크기를 변경해야합니다. 그래서 우리는 키에 논리를 피해야한다. 때때로 우리는 키와 사회적 ID (정수 값)를 사용할 수 있지만, 나도 그 피하십시오. 프로젝트를 확장 할 전망을 가지고 자하는 경우가 너무 (고유 식별자 SQL 유형) GUID를 사용하는 것이 좋습니다.

    우리는 테이블의 기본 키는 "비즈니스 로직을"이없는 것을 명심해야하고 그것이 속해있는 기록의 식별해야합니다. 이 간단한 규칙의 int 특히 신원 INT 따르는 것은 매우 좋은 솔루션입니다. VARCHAR에 대해 물어 난 당신이 "사람"테이블에 키로서, 예를 들어 "전체 이름"을 사용하여 의미 있다고 생각한다. 그러나 우리는 "조지 A. 뭔가"에서 "조지 뭔가"에서 이름을 변경하려면 어떻게해야할까요? 그리고 필드는 어떤 크기가 될 것인가? 우리가 크기를 변경하는 경우 우리는 너무 모든 해외 테이블의 크기를 변경해야합니다. 그래서 우리는 키에 논리를 피해야한다. 때때로 우리는 키와 사회적 ID (정수 값)를 사용할 수 있지만, 나도 그 피하십시오. 프로젝트를 확장 할 전망을 가지고 자하는 경우가 너무 (고유 식별자 SQL 유형) GUID를 사용하는 것이 좋습니다.

  13. ==============================

    13.이것은 아주 오래된 질문이 마음에 유지, 난 여전히 대리 키 모피 미래의 리더와 VARCHAR를 사용하는 경우를 만들고 싶어 :

    이것은 아주 오래된 질문이 마음에 유지, 난 여전히 대리 키 모피 미래의 리더와 VARCHAR를 사용하는 경우를 만들고 싶어 :

  14. from https://stackoverflow.com/questions/1301165/should-i-design-a-table-with-a-primary-key-of-varchar-or-int by cc-by-sa and MIT license