【问题标题】:Delete operation - Multiple tables with many to many relationship删除操作 - 具有多对多关系的多个表
【发布时间】:2014-07-21 17:18:19
【问题描述】:

我有四个表和三个联结表来指示多对多关系。 这是使用项目二进制文件将包含多个应用程序二进制文件的一般信息创建的,每个应用程序二进制文件可以由多个存档、共享对象、对象、二进制文件等构建。每个存档或共享对象或二进制文件可以由多个源文件(.c , .cpp, .hpp, .h , sh , .java)。

问题如下。


1.这个设计够好吗?或者有更好的方法来做到这一点。
2.如果我需要删除一个项目二进制文件,可以用什么sql查询。
3. 如果我只需要从 BinaryList_table 中删除一些二进制文件,什么可以是 sql 查询及其对其他表的影响,因为存在多对多关系。

ProjectList_table
-----
ProjectBinaryId ProjectBinary   VersionInfo etc.    Market
1               NTG5_App          1.2               Japan
2               NTG5_App          1.3               Europe

------
AppList_table
-------
Appld   ApplicationBinary   VersionInfo
1       CarFU   
2       NavHU               1.1
3       MediaHU 
4       Connectivity    
5       QNX binaries    
6       NavHU               1.2
-------

ProjectBinary_AppJunctionTable  
-------
ProjectBinaryId AppId
1               1
1               2
1               3
1               4
1               5
2               5
2               4
2               6
------------------


BInaryList_Table    
--------------  
BinaryId    BinaryFileName  LicenseDetails
1           .so 
2           .a  
3           .so 
4           binary  
5           .a  
6           .a  
7           .so 
8           .o  
9           .a  
10          .so 
11          .so 
12          .a  
13          binary (shell command wo extn)  
-------------------------

App_BinaryJunctionTable 
---------------------
AppId   BinaryId
1        1
1        2
1        3
1        4
2        5
2        3
3        7
3        8
4        1
4        10
5        11
5        12
5        13
-----------

SourceInfo_Table
--------        
SourceId    Source file            License Details
1           .c, .cpp, .h,.sh .etc   
2           .c, .cpp, .h,.sh .etc   
3           .c, .cpp, .h,.sh .etc   
4           .c, .cpp, .h,.sh .etc   
5           .c, .cpp, .h,.sh .etc   
6           .c, .cpp, .h,.sh .etc   
7           .c, .cpp, .h,.sh .etc   
8           .c, .cpp, .h,.sh .etc   
9           .c, .cpp, .h,.sh .etc   
10          .c, .cpp, .h,.sh .etc   
11          .c, .cpp, .h,.sh .etc   
12          .c, .cpp, .h,.sh .etc   
13          .c, .cpp, .h,.sh .etc   
------------

Binary_SourceJunctionTable
-------------
BinaryId    SourceId
1           1
1           2
1           3
1           4
2           5
2           3
2           6
2           7
4           1
4           2
4           8
4           9
-------------

嗨凯文

首先,我创建了所有项目、应用程序和源信息表。然后我成功创建了 projectbinary_AppJunctionTable,但是当我尝试创建 app_binaryJunction 表时。我收到如下粘贴的错误 -

-ERROR 1022: Can't write; duplicate key in table 'appid_objid_junctiontable'
SQL Statement:
CREATE TABLE `trial`.`appid_objid_junctiontable` (
  `Id` INT NOT NULL,
  `app_id` INT NULL,
  `obj_id` INT NULL,
  PRIMARY KEY (`Id`),
  INDEX `app_id_idx` (`app_id` ASC),
  INDEX `obj_id_idx` (`obj_id` ASC),
  CONSTRAINT `app_id_fk`
    FOREIGN KEY (`app_id`)
    REFERENCES `trial`.`applisttable` (`Appld`)
    ON DELETE NO ACTION
    ON UPDATE NO ACTION,
  CONSTRAINT `obj_id_fk`
    FOREIGN KEY (`obj_id`)
    REFERENCES `trial`.`objectlist_table` (`ObjectId`)
    ON DELETE NO ACTION
    ON UPDATE NO ACTION)

-- 请帮忙。

7 月 21 日编辑

嗨,凯文,感谢您的 sql 查询。我尝试在 projectbinary 表和 applisttable 之间创建联结表,但失败如下。

CREATE TABLE trial.projid_appid_junctiontable ( 
  proj_id INT NOT NULL, 
  app_id INT NOT NULL, 
  PRIMARY KEY (proj_id, app_id), 
  FOREIGN KEY (proj_id) REFERENCES trial.projectlisttable (ProjectBinaryId) ON DELETE NO     ACTION ON UPDATE NO ACTION, 
  FOREIGN KEY (app_id) REFERENCES trial.applisttable (AppId) ON DELETE NO ACTION
);
Error code: 1215 Cannot add foreign key constraint.

【问题讨论】:

    标签: mysql sql database database-design many-to-many


    【解决方案1】:

    设计适合您提供的尽可能多的信息。我唯一的抱怨是“SourceInfo_Table”并不平坦,这意味着它的“源文件”列具有多个值。您应该制作另一个连接表。将其称为“sourceInfo_fileTypes”或您想要的任何名称。把 sourceID 和文件类型,每个文件类型一个记录。理想情况下,您还会有另一个名为 fileTypes 的表,而是使用外键链接到它们。

    至于删除项目二进制文件的SQL。您必须记住它们具有外键依赖项(假设您设置了约束)。有很多方法可以解决这个问题。同样,理想情况下,您应该在每个外键上都有 ON DELETE CASCADE。这意味着当您从项目列表中删除某些内容时,它会自动在其他地方删除。如果您没有打开它并且已经设置了约束,那么您想像下面这样删除约束,然后将其与子句一起添加。

    DROP CONSTRAINT:(每个都做)

    ALTER TABLE ProjectBinary_AppJunctionTable
    DROP CONSTRAINT ProjectBinaryId; 
    

    ADD CONSTRAINT WITH ON DELETE CASCADE:(对每个都做)

    ALTER TABLE ProjectBinary_AppJunctionTable
    ADD FOREIGN KEY (ProjectBinaryId)
    REFERENCES ProjectList_table(ProjectBinaryId) ON DELETE CASCADE
    

    此外,要简单地从这些表之一中删除某些内容,请使用下面的通用代码。此外,如果您为每个表设置正确的依赖关系,上述代码应该会处理所有依赖关系。

    DELETE FROM one_of_your_tables
    WHERE on_of_you_columns=some_value_in_the_column;
    

    7 月 18 日编辑: 您不需要说约束,如果它是外键,它会自动成为约束,说约束的唯一原因是命名键。您不需要在此处对其进行索引,因为它被索引为另一个表的主键。您不需要另一个 ID 作为主键,它是无用的。您需要做的就是说 app_id 与 obj_id 结合创建一个主键,这意味着这两列在另一行上永远不会相同。试试下面的代码,看看效果如何。

    CREATE TABLE trial.appid_objid_junctiontable ( 
    app_id INT NOT NULL, 
    obj_id INT NOT NULL, 
    PRIMARY KEY (app_id, obj), 
    FOREIGN KEY (app_id) REFERENCES trial.applisttable (Appld) ON DELETE NO ACTION ON UPDATE NO ACTION, 
    FOREIGN KEY (obj_id) REFERENCES trial.objectlist_table (ObjectId) ON DELETE NO ACTION
    )
    

    【讨论】:

    • 谢谢凯文,这是很好的信息。至于您对“SourceInfo_table”的关注,我的意思是源文件可以是 .c 或 .cpp 或 .h 中的任何一个,并且一条记录中的源文件不多。关于“ON DELETE CASCADE”,我会了解更多,如果有任何问题,我会向您提问。
    • 没问题。关于那张桌子,我认为一张桌子上的所有这些类型。但无论哪种方式,在一个完美的世界中,您都可以拥有另一个带有文件扩展名的表。这取决于你想要它的标准化程度。许多人会反对,因为这可能是不必要的连接,导致速度延迟。
    • 嗨 Kevin,ProjectBinaryId 和 AppId 都可以是 ProjectBinary_AppJunctionTable 中的外键吗?
    • 是的,每个键都是外键。您可以根据需要拥有任意数量的外键。这两个键也组合起来构成主键,因为它们唯一标识每一行。
    • 嗨 Kevin,我需要你的帮助来在 mysql 中创建所有这些连接表,即 ProjectBinary_AppJunctionTable、App_BinaryJunctionTable。我试图创建那些,我认为在一个表中创建的外键不能是另一个表中的外键。能否请您发布 SQL 查询。
    猜你喜欢
    • 1970-01-01
    • 2021-10-27
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-08-23
    相关资源
    最近更新 更多