0

데이터베이스가 잘 작동하는지 확인하기 만하면됩니다. 그리고 내가 아니라면 나는 여기서 잘못된 것을하고 있습니다.
나는 다음과 같은 테이블이 있습니다많은 동적 데이터베이스 관계 문제가 발생했습니다.

TableA{TableAID,...} 
TableB{TableBID,...} 
TableC{TableCID,...} 
etc. 

을 그리고 난 '뉴스 피드'의 일종처럼 사용하는 하나 개의 테이블이있다. 어떤 테이블 A, B, C에 무언가를 추가 할 때도이 테이블에 행을 추가합니다.

Feed{FeedID, TypeID, ReferenceID,...} 

FeedID


TypeID 내가 테이블 A, B, C에서이 테이블의 행에 알이 ID 유형 테이블을 참조하고 기초 번호 PK 자동 증분을한다.
ReferenceId은 표 A, B, C의 항목 ID입니다.
A, B, C 테이블에는 모두 다른 필드가 있습니다.
이제 피드 데이터를 가져 오려면이 테이블의 각 데이터를 응용 프로그램에서 사용하기 위해 데이터를 가져와야합니다.

... 
CASE Feed.TypeId    
       WHEN 1 THEN tableA.someData 
          WHEN 2 THEN tableB.someData 
          WHEN 3 THEN tableC.someData 
      END AS Data, 
... 

enter image description here

+0

1 : 1 확장 테이블은 공정하게 관련된 쿼리를 만듭니다. 나는 하나의 테이블을 선호한다. 각 피드 유형과 관련이없는 속성의 null 허용 열이있는 경우 – Andomar

+1

A, B 및 C가 왜 다른 테이블입니까? 모델을 추상화하고 모델을 복잡하게 만드는 대신 유형 속성이있는 테이블을 하나만 만들면 어떨까요? 테이블을 기반으로하는 추가 열과 관련된 쿼리를 작성해야하는 경우 해당 쿼리는 해당 유형을 기반으로하는 추가 열을 포함하여 비슷하게 복잡 할 수 있습니다. 즉, @Andomar가 제안했듯이 모든 가능한 열은 다른 테이블에 있고 일부는 형식에 따라 Nullable이 될 수 있습니다. –

+0

그들은 별도의 엔티티이기 때문에 A는 10 개의 열, B 3 열 및 C 5를 가질 수 있습니다. – 1110

답변

1

특정 용도로 적합하지 않으면 수퍼 유형 - 하위 유형 모델이 "반대"됩니다.

enter image description here

그래서 DDL이 구조에서 읽기 위해, 먼저보기를 만들 지금

CREATE TABLE Feed ( 
     FeedID    integer IDENTITY(1,1) not null 
    , FeedType    char(1) not null 
    -- Common_Columns_Here 
    , Common_Column  varchar(20) 
); 
ALTER TABLE Feed ADD CONSTRAINT pk_Feed PRIMARY KEY (FeedID) ; 


CREATE TABLE Feed_A ( 
     FeedID    integer not null 
    -- A_Specific_Columns_Here 
    , A_Specific_Column varchar(20) 
); 
ALTER TABLE Feed_A ADD 
    CONSTRAINT pk_Feed_A PRIMARY KEY (FeedID) 
, CONSTRAINT fk1_Feed_A FOREIGN KEY (FeedID) REFERENCES Feed(FeedID) ; 


CREATE TABLE Feed_B (
     FeedID    integer not null 
    -- B_Specific_Columns_Here 
    , B_Specific_Column varchar(20) 
); 
ALTER TABLE Feed_B ADD 
    CONSTRAINT pk_Feed_B PRIMARY KEY (FeedID) 
, CONSTRAINT fk1_Feed_B FOREIGN KEY (FeedID) REFERENCES Feed(FeedID) ; 


CREATE TABLE Feed_C ( 
     FeedID    integer not null 
    -- C_Specific_Columns_Here 
    , C_Specific_Column varchar(20) 
); 
ALTER TABLE Feed_C ADD 
    CONSTRAINT pk_Feed_C PRIMARY KEY (FeedID) 
, CONSTRAINT fk1_Feed_C FOREIGN KEY (FeedID) REFERENCES Feed(FeedID) ; 

같이 보입니다

create view vFeed as 
select 
     f.FeedID 
    , FeedType 
    , Common_Column 
    , A_Specific_Column 
    , B_Specific_Column 
    , C_Specific_Column 
from  Feed as f 
left join Feed_A as a on (a.FeedID = f.FeedID and f.FeedType = 'A') 
left join Feed_B as b on (b.FeedID = f.FeedID and f.FeedType = 'B') 
left join Feed_C as c on (c.FeedID = f.FeedID and f.FeedType = 'C') 
; 

내가 선택하고자 할 때 어떻게되는지 봐 I 이 알고있는 데이터는 피드 A에서 나온 것입니다. 이 쿼리에는 FeedType이 지정되어 있지 않으며 Feed_A (및 공통 열)에 속하는 열 이름 만 사용합니다.

select 
     FeedID 
    , Common_Column 
    , A_Specific_Column 
from vFeed; 

enter image description here

공지 사항이 실행 계획은 FeedFeed_A 테이블을 보여줍니다, 쿼리 최적화 프로그램 제거 테이블 _B_C; 그 둘을 만질 필요가 없습니다.

즉, 검색어의 특정 열만 사용하여 특정 피드 데이터를 요청하고 옵티마이 저가 다른 모든 것을 정렬하도록 할 수 있습니다. 예를 들어 CASE ... WHEN .. 곡예는 필요 없습니다.

+0

왜 이것이 반대라고 생각합니까? 만약 내가 모든 피드를 얻을 때보 다 이런 식으로 설계한다면, 나는 다른 테이블에있는 아이템의 ID를 가지고 있지 않기 때문에 어느 테이블에 참여할 지 알 수 없습니다. – 1110

+0

@ 1110; 업데이트 된 응답 –

+0

@ 1100을보고이 구조체를로드하려면 먼저 'Feed' 테이블에 삽입하여'FeedID'를 얻은 다음'_A','_B','_C' 중 하나에 삽입하십시오. 나는 그것을 돌볼 수있는 저장 프로 시저를 제안 할 것이다. 이렇게하면 - 읽기와 ** sp **로드보기가 가능하므로 응용 프로그램 계층에서 DB 스키마 (변경 사항)를 분리 할 수 ​​있습니다. INSERT, UPDATE 트리거를 뷰에 사용할 수도 있습니다. –

0

내가 내 댓글에 제시된 바와 같이 (A, B, C) 내가 첫 번째 쿼리에서 모든 테이블에 가입

: 내 쿼리에서 내가 좋아하는 많은 SELECT CASE CLAUSE을 사용하여이를 얻을 수 있습니다 (그리고 @ Andomar의 지혜와 함께),이 같은 일이 잘 작동 할 것이라는 점을 생각한다 :

CREATE TABLE dbo.FeedTypes 
(
    FeedTypeID INT IDENTITY(1,1) PRIMARY KEY, 
    SomedataA INT, 
    SomedataB VARCHAR(32), 
    SomedataC DATETIME 
    --, ... other columns 
); 

CREATE TABLE dbo.Feeds 
(
    FeedID INT IDENTITY(1,1) PRIMARY KEY, 
    FeedTypeID INT NOT NULL FOREIGN KEY 
    REFERENCES dbo.FeedTypes(FeedTypeID) 
    --, ... other columns 
); 

당신이주고 위해 관련 컬럼에 데이터의 존재/부재를 적용 할 수 n 유형을 사용합니다. 그러나 피드가 형식을 쉽게 변경할 수 있다면 꽤 복잡한 논리를 사용해야합니다 (현재 모델에서와 같이).

0

Feed 테이블의 '뉴스 피드'에 표시하려는 모든 데이터를 추가하십시오. 그것은 중복 데이터이지만 장기적으로 당신의 삶을 훨씬 쉽게 만들어줍니다.

또한 뉴스 피드가 역사적으로 정확한지 확인합니다. 즉, 세 테이블 중 하나에서 레코드를 업데이트하면 "이전"피드 데이터가 새 값으로 업데이트되는 대신 그대로 유지됩니다.

관련 문제