[SQL] 그것은 여러 외국 키로 한 열을 참조 할 수 있습니까?
SQL그것은 여러 외국 키로 한 열을 참조 할 수 있습니까?
나는 몇 테이블을 가지고 있고, 여러 개의 다른 테이블에 PDF 테이블에서 하나의 열을 참조 할.
예를 들어 PDF 테이블은 다음과 같이 출력 모양을 선택하는 경우 :
ITEM_TYPE ITEM_ID QUANTITY
1 23 3
2 12 1
그것은 나에게 말한다 :
PDF는 3 자동차 바퀴 제품, 1 차 템플릿 헤더 위있다;
나는 SQL 코드를 작성하지만, 제대로 작동하지 않습니다 :
CREATE TABLE `pdf_created` (
`id` INT(10) UNSIGNED NOT NULL UNIQUE AUTO_INCREMENT,
`pdf_id` INT(10) NOT NULL,
`item_type` INT(3) UNSIGNED NOT NULL,
`item_id` INT(10) UNSIGNED NOT NULL,
`quantity` INT(3) NOT NULL,
PRIMARY KEY (`id`),
KEY `FK_pdf_id` (`pdf_id`),
CONSTRAINT `FK_pdf_id` FOREIGN KEY (`pdf_id`) REFERENCES `pdf` (`id`),
KEY `FK_item_type` (`item_type`),
CONSTRAINT `FK_item_type` FOREIGN KEY (`item_type`) REFERENCES `item` (`id`) ON DELETE CASCADE ON UPDATE CASCADE,
KEY `FK_item_id` (`item_id`),
CONSTRAINT `FK_item_id` FOREIGN KEY (`item_id`) REFERENCES `product` (`id`) ON DELETE CASCADE ON UPDATE CASCADE,
CONSTRAINT `FK_item_id` FOREIGN KEY (`item_id`) REFERENCES `service` (`id`) ON DELETE CASCADE ON UPDATE CASCADE,
CONSTRAINT `FK_item_id` FOREIGN KEY (`item_id`) REFERENCES `header` (`id`) ON DELETE CASCADE ON UPDATE CASCADE
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
CREATE TABLE `header` (
`id` INT(10) UNSIGNED NOT NULL UNIQUE AUTO_INCREMENT,
`title` VARCHAR(255),
`desc` VARCHAR(65535),
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
CREATE TABLE `service` (
`id` INT(10) UNSIGNED NOT NULL UNIQUE AUTO_INCREMENT,
`desc` VARCHAR(65535) NOT NULL,
`price` DECIMAL(5,2) NOT NULL,
`active` INT(1) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
CREATE TABLE `product` (
`id` INT(10) UNSIGNED NOT NULL UNIQUE AUTO_INCREMENT,
`category_id` INT(3) UNSIGNED NOT NULL,
`symbol` VARCHAR(255),
`desc` VARCHAR(65535),
`price` DECIMAL(5,2) NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
그것을 만들 수 있습니다?
해결법
-
==============================
1.아니.
아니.
즉, 당신은 외래 키 제약 조건이 방법을 만들 수 없습니다. 당신은 그러나, 외래 키 제약 조건없이 외래 키를 사용할 수 있습니다.
외래 키는 모두, 다른 테이블 (또는 같은 테이블에서 다른 레코드) 조인에서 사용할 수있는 기본 키의 값입니다. 당신이 필요로하는 모든이에 대한 조인 값을 사용하는 경우 사실, 당신은, 기본 키가 아닌 필드를 참조 할 수 있습니다.
그러나 외래 키 제약 조건은 기본 키의 같은 테이블의 모든 외래 키 값, 참조 된 테이블이 그와 기록을 가지고있는 규칙을 시행 할 수있는 데이터베이스를 알려줍니다. PDF 파일 테이블의 모든 외래 키는 4 가지의 모든 테이블이 당신을 위해 작동하지 않습니다 기본 키를 가지고 있음을 시행. 그래서 가서 다른 기록을 참조 할 필드를 사용하지만, 간단히 외래 키 제약 조건을 만들 수 없습니다.
-
==============================
2.당신이 만난 문제는 다형성 협회라고
당신이 만난 문제는 다형성 협회라고
이 질문을 참조하십시오 : MySQL의 - 조건부 외래 키 제약 조건을
-
==============================
3.그것은 수 있어야한다. 하나의 잠재적 인 문제는 세 개의 외래 키 제약 조건이 동일한 이름을 가지고있다.
그것은 수 있어야한다. 하나의 잠재적 인 문제는 세 개의 외래 키 제약 조건이 동일한 이름을 가지고있다.
-
==============================
4.아니, 하나 개의 외래 키 필드는 참조 하나의 테이블을 의미한다.
아니, 하나 개의 외래 키 필드는 참조 하나의 테이블을 의미한다.
당신은 당신이 설명하는대로 FK 제약 조건을 가지고 있었다 경우 ITEM_ID 필드는 모두 세 개의 테이블에 동일한 기본 키 값을 참조 할 것. 세 가지 다른 테이블에서 원하는 기본 키가 서로 다른 기본 키를했을 가능성이 매우 높다 할 것이다.
당신이 원하는 것은 테이블 제품, 헤더, 및 서비스의 기준 기록에 하나 개의 레코드 (행)입니다. 그렇게하는 방법은 세 가지 분야, 각 외부 키를 사용하는 것입니다.
나는 또한 항목 테이블이 필요한 세 개의 외래 키를 가지고 있음을 알 수 있습니다. 당신은 PDF 테이블이 하나 개의 필드 참조 항목 및 항목 참조의 레코드 세 개의 다른 테이블이있을 수 있습니다.
-
==============================
5.나중에 그것의 가능한 외래 키 제약 조건 이름이 같은 다른해야 및 기본 키와 외래 키 테이블 컬럼이 같은 동일한 데이터 유형을 가져야한다 ..
나중에 그것의 가능한 외래 키 제약 조건 이름이 같은 다른해야 및 기본 키와 외래 키 테이블 컬럼이 같은 동일한 데이터 유형을 가져야한다 ..
CREATE TABLE `neo_address_t` ( `address_id` varchar(8) NOT NULL, `address_line_1` varchar(45) NOT NULL, `address_line_2` varchar(45) NOT NULL, `address_line_3` varchar(45) NOT NULL, `address_city` varchar(45) NOT NULL, `address_zipcode` varchar(45) NOT NULL, `address_state` varchar(45) NOT NULL DEFAULT 'Karnataka', `address_country` varchar(45) NOT NULL DEFAULT 'INDIA', `created_by` varchar(8) DEFAULT NULL, `created_on` timestamp NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, `last_modified_by` varchar(8) DEFAULT NULL, `last_modified_date` timestamp NULL DEFAULT '0000-00-00 00:00:00', `Refer_ID` int(11) DEFAULT NULL, `a_id` varchar(255) DEFAULT NULL, `referenceid` varchar(255) DEFAULT NULL, PRIMARY KEY (`address_id`), KEY `hospital_ID_FK_idx` (`Refer_ID`), CONSTRAINT `Patient_ID_FK` FOREIGN KEY (`Refer_ID`) REFERENCES `neo_patient_t` (`patient_ID`) ON DELETE NO ACTION ON UPDATE NO ACTION, CONSTRAINT `hospital_ID_FK` FOREIGN KEY (`Refer_ID`) REFERENCES `neo_hospital_t` (`hospital_id`) ON DELETE NO ACTION ON UPDATE CASCADE, CONSTRAINT `staff_ID_FK` FOREIGN KEY (`Refer_ID`) REFERENCES `neo_staff_t` (`staff_ID`) ON DELETE NO ACTION ON UPDATE NO ACTION ) ENGINE=InnoDB DEFAULT CHARSET=utf8$$
-
==============================
6.이론적으로는 단일 컬럼에 여러 개의 외래 키를 적용 할 수 없습니다. 또는 당신은 당신이 여러 테이블에 존재 입력을 확인하고 필요한 작업을 수행 절차를 사용하여이를 적용 할 수 있습니다. 특정 테이블에 모든 작업이 무결성을 위반 그렇지 않으면 것 리드를 필요한 조건의 유효성을 검사하는 절차에 의해 수행되어야 함을주의하십시오.
이론적으로는 단일 컬럼에 여러 개의 외래 키를 적용 할 수 없습니다. 또는 당신은 당신이 여러 테이블에 존재 입력을 확인하고 필요한 작업을 수행 절차를 사용하여이를 적용 할 수 있습니다. 특정 테이블에 모든 작업이 무결성을 위반 그렇지 않으면 것 리드를 필요한 조건의 유효성을 검사하는 절차에 의해 수행되어야 함을주의하십시오.
-
==============================
7.네, 가능합니다. 그것은 조금 이상한 것 같다 경우에도 마찬가지입니다.
네, 가능합니다. 그것은 조금 이상한 것 같다 경우에도 마찬가지입니다.
먼저 나는 그것이 작동하는지 증언을 내 MySQL의 워크 벤치의 스크린 샷을 보여 드리고자합니다.
... 그리고 "어쩌면 당신은 변경 사항을 적용하는 것을 잊었다"말하는 사람들을 위해 ... 여기 스키마 브라우저의 스크린 샷입니다 :
마지막으로 몇 가지 예를 들어 데이터를 내 보낸 덤프 :
-- MySQL dump 10.13 Distrib 5.7.12, for Win64 (x86_64) -- -- Host: localhost Database: multiple_foreign_keys -- ------------------------------------------------------ -- Server version 5.7.17-log /*!40101 SET @OLD_CHARACTER_SET_CLIENT=@@CHARACTER_SET_CLIENT */; /*!40101 SET @OLD_CHARACTER_SET_RESULTS=@@CHARACTER_SET_RESULTS */; /*!40101 SET @OLD_COLLATION_CONNECTION=@@COLLATION_CONNECTION */; /*!40101 SET NAMES utf8 */; /*!40103 SET @OLD_TIME_ZONE=@@TIME_ZONE */; /*!40103 SET TIME_ZONE='+00:00' */; /*!40014 SET @OLD_UNIQUE_CHECKS=@@UNIQUE_CHECKS, UNIQUE_CHECKS=0 */; /*!40014 SET @OLD_FOREIGN_KEY_CHECKS=@@FOREIGN_KEY_CHECKS, FOREIGN_KEY_CHECKS=0 */; /*!40101 SET @OLD_SQL_MODE=@@SQL_MODE, SQL_MODE='NO_AUTO_VALUE_ON_ZERO' */; /*!40111 SET @OLD_SQL_NOTES=@@SQL_NOTES, SQL_NOTES=0 */; -- -- Table structure for table `header` -- DROP TABLE IF EXISTS `header`; /*!40101 SET @saved_cs_client = @@character_set_client */; /*!40101 SET character_set_client = utf8 */; CREATE TABLE `header` ( `id` int(10) unsigned NOT NULL AUTO_INCREMENT, `title` varchar(255) DEFAULT NULL, `desc` varchar(255) DEFAULT NULL, PRIMARY KEY (`id`), UNIQUE KEY `id` (`id`) ) ENGINE=InnoDB AUTO_INCREMENT=43 DEFAULT CHARSET=utf8; /*!40101 SET character_set_client = @saved_cs_client */; -- -- Dumping data for table `header` -- LOCK TABLES `header` WRITE; /*!40000 ALTER TABLE `header` DISABLE KEYS */; INSERT INTO `header` VALUES (42,'Header','Test Header'); /*!40000 ALTER TABLE `header` ENABLE KEYS */; UNLOCK TABLES; -- -- Table structure for table `pdf_created` -- DROP TABLE IF EXISTS `pdf_created`; /*!40101 SET @saved_cs_client = @@character_set_client */; /*!40101 SET character_set_client = utf8 */; CREATE TABLE `pdf_created` ( `id` int(10) unsigned NOT NULL AUTO_INCREMENT, `pdf_id` int(10) NOT NULL, `item_type` int(3) unsigned NOT NULL, `item_id` int(10) unsigned NOT NULL, `quantity` int(3) NOT NULL, PRIMARY KEY (`id`), UNIQUE KEY `id` (`id`), KEY `fk_item_to_product_idx` (`item_id`), CONSTRAINT `fk_item_to_header` FOREIGN KEY (`item_id`) REFERENCES `header` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, CONSTRAINT `fk_item_to_product` FOREIGN KEY (`item_id`) REFERENCES `product` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION, CONSTRAINT `fk_item_to_service` FOREIGN KEY (`item_id`) REFERENCES `service` (`id`) ON DELETE NO ACTION ON UPDATE NO ACTION ) ENGINE=InnoDB AUTO_INCREMENT=2 DEFAULT CHARSET=utf8; /*!40101 SET character_set_client = @saved_cs_client */; -- -- Dumping data for table `pdf_created` -- LOCK TABLES `pdf_created` WRITE; /*!40000 ALTER TABLE `pdf_created` DISABLE KEYS */; INSERT INTO `pdf_created` VALUES (1,2,5,42,1); /*!40000 ALTER TABLE `pdf_created` ENABLE KEYS */; UNLOCK TABLES; -- -- Table structure for table `product` -- DROP TABLE IF EXISTS `product`; /*!40101 SET @saved_cs_client = @@character_set_client */; /*!40101 SET character_set_client = utf8 */; CREATE TABLE `product` ( `id` int(10) unsigned NOT NULL AUTO_INCREMENT, `category_id` int(3) unsigned NOT NULL, `symbol` varchar(255) DEFAULT NULL, `desc` varchar(255) DEFAULT NULL, `price` decimal(5,2) NOT NULL, PRIMARY KEY (`id`), UNIQUE KEY `id` (`id`) ) ENGINE=InnoDB AUTO_INCREMENT=43 DEFAULT CHARSET=utf8; /*!40101 SET character_set_client = @saved_cs_client */; -- -- Dumping data for table `product` -- LOCK TABLES `product` WRITE; /*!40000 ALTER TABLE `product` DISABLE KEYS */; INSERT INTO `product` VALUES (42,13,'product','desc',10.00); /*!40000 ALTER TABLE `product` ENABLE KEYS */; UNLOCK TABLES; -- -- Table structure for table `service` -- DROP TABLE IF EXISTS `service`; /*!40101 SET @saved_cs_client = @@character_set_client */; /*!40101 SET character_set_client = utf8 */; CREATE TABLE `service` ( `id` int(10) unsigned NOT NULL AUTO_INCREMENT, `desc` varchar(255) NOT NULL, `price` decimal(5,2) NOT NULL, `active` int(1) NOT NULL, PRIMARY KEY (`id`), UNIQUE KEY `id` (`id`) ) ENGINE=InnoDB AUTO_INCREMENT=43 DEFAULT CHARSET=utf8; /*!40101 SET character_set_client = @saved_cs_client */; -- -- Dumping data for table `service` -- LOCK TABLES `service` WRITE; /*!40000 ALTER TABLE `service` DISABLE KEYS */; INSERT INTO `service` VALUES (42,'some service',5.00,1); /*!40000 ALTER TABLE `service` ENABLE KEYS */; UNLOCK TABLES; /*!40103 SET TIME_ZONE=@OLD_TIME_ZONE */; /*!40101 SET SQL_MODE=@OLD_SQL_MODE */; /*!40014 SET FOREIGN_KEY_CHECKS=@OLD_FOREIGN_KEY_CHECKS */; /*!40014 SET UNIQUE_CHECKS=@OLD_UNIQUE_CHECKS */; /*!40101 SET CHARACTER_SET_CLIENT=@OLD_CHARACTER_SET_CLIENT */; /*!40101 SET CHARACTER_SET_RESULTS=@OLD_CHARACTER_SET_RESULTS */; /*!40101 SET COLLATION_CONNECTION=@OLD_COLLATION_CONNECTION */; /*!40111 SET SQL_NOTES=@OLD_SQL_NOTES */; -- Dump completed on 2018-08-27 10:31:41
당신은 SQL 스크립트 편집기 대신 그것을 테스트하려는 경우 사용 MySQL의 워크 벤치에 '데이터 가져 오기 / 복원'.
세 가지 모두 동일한 ID를 얻을 것이다 경우는 운이 우연의 일치 일 것입니다 있기 때문에 당신은 pdf_created.item_id 참조하는 제품, 헤더 및 서비스 테이블에 자동 증가를 사용하지 않아야합니다. 당신은 ID (항목의 ID)를 할당해야합니다.
from https://stackoverflow.com/questions/15547276/is-it-possible-to-reference-one-column-as-multiple-foreign-keys by cc-by-sa and MIT license
'SQL' 카테고리의 다른 글
[SQL] 어떻게 내가 같은 테이블에서 2 개 행을 비교합니까 (SQL 서버) (0) | 2020.06.03 |
---|---|
[SQL] 많은 인덱스가있는 테이블에 대한 느린 대량 삽입 (0) | 2020.06.03 |
[SQL] T-SQL 하위 쿼리 최대 (일)과 조인 (0) | 2020.06.03 |
[SQL] 어떻게 엔티티 프레임 워크는 문자 (N) 필드에 매핑 특정 컬럼에 대한 검색 자동 트림 값으로 구성 할 수 있습니다? (0) | 2020.06.03 |
[SQL] PostgreSQL를 9.3로 가져 오기 엑셀 데이터 (0) | 2020.06.03 |