Mysql 多个表之间的SQL多对多关系
我有一个数据库,我正试图在SQL上创建,我正试图将这些关系连接在一起。有三张表格:超级英雄、力量和超级英雄力量。表superhero和power是一种多对多关系,由表Superherower表示 对于表之间的外键(以及其他所有键),下面的语法是否正确?此外,在这些表格的设置方面是否有其他建议Mysql 多个表之间的SQL多对多关系,mysql,sql,Mysql,Sql,我有一个数据库,我正试图在SQL上创建,我正试图将这些关系连接在一起。有三张表格:超级英雄、力量和超级英雄力量。表superhero和power是一种多对多关系,由表Superherower表示 对于表之间的外键(以及其他所有键),下面的语法是否正确?此外,在这些表格的设置方面是否有其他建议 CREATE TABLE superhero( id INT NOT NULL AUTO_INCREMENT, heroName VARCHAR(255) NOT NULL, firstName VAR
CREATE TABLE superhero( id INT NOT NULL AUTO_INCREMENT,
heroName VARCHAR(255) NOT NULL,
firstName VARCHAR(255),
lastName VARCHAR(255),
firstAppearance DATE,
gender VARCHAR(255),
bio TEXT,
universe VARCHAR(255),
PRIMARY KEY(id)
) ENGINE=InnoDB;
CREATE TABLE power(
id INT NOT NULL AUTO_INCREMENT,
name VARCHAR(255) NOT NULL,
description TEXT NOT NULL,
PRIMARY KEY(id)
) ENGINE=InnoDB;
CREATE TABLE superheroPower(
superheroID INT,
powerID INT,
PRIMARY KEY(superheroID, powerID),
FOREIGN KEY(superheroID) REFERENCES superhero(id),
FOREIGN KEY(powerID) REFERENCES power(id)
) ENGINE=InnoDB;
编辑[1]:这是一个版本的SQL代码,关于我将如何做
CREATE TABLE superhero
(
Superheo_id INT NOT NULL AUTO_INCREMENT,
heroName VARCHAR(255) NOT NULL,
firstName VARCHAR(255)NULL,
lastName VARCHAR(255)NULL,
firstAppearance DATE NULL,
gender VARCHAR(255) NULL,
bio TEXT NULL,
universe VARCHAR(255) NULL,
CONSTRAINT SUPERHERO_PK PRIMARY KEY(SUPERHERO_id)
);
CREATE TABLE power
(
POWER_id INT NOT NULL AUTO_INCREMENT,
name VARCHAR(255) NOT NULL,
description TEXT NOT NULL,
CONSTRAINT POWER_PK PRIMARY KEY(POWER_id)
);
CREATE TABLE superheroPower
(
superheroID INT DEFAULT(0) NOT NULL,
powerID INT DEFAULT(0) NOT NULL,
CONSTRAINT SUPERHEROPOWERS_SUPERHERO_FK FOREIGN KEY(superheroID) REFERENCES superhero(id),
CONSTRAINT SUPERHEROPOWERS_POWERS_FK FOREIGN KEY(powerID) REFERENCES power(id)
);
编辑[2]:您可以将null更改为非null,反之亦然,具体取决于您是否希望用户在不安装其他信息的情况下移动过去。我以前从未在我的sql表中使用过自动增量,所以对我来说,这是我刚从你那里学到的新东西是的,那里的一切看起来都很好。但是
请注意: 对于
gender
列,我们将使用较短的数据类型;我不认为我们需要255个字符来表达。(对强制执行的行的最大大小有限制)。如果只有几个值,我们会考虑<代码>枚举< /代码>数据类型。< /P>
我们还可能在其中几个列上添加notnull
约束,例如heroname、firstname、lastname。我们还可能添加默认值'
。有时,出于某种原因,我们确实需要允许空值,但我们尽可能使用notnull
我对文本列犹豫不决。使用TEXT
datatype并没有什么错,但我怀疑它们可能“隐藏”了一些信息,这些信息最好存储在其他列中
对于外键,我们将按照我们使用的模式为约束指定一个名称,还可能在更新级联时添加,在删除级联时添加
CONSTRAINT FK_superheroPower_power FOREIGN KEY (powerID)
REFERENCES power(id) ON UPDATE CASCADE ON DELETE CASCADE
关于标识符(表名和列名)的说明
按照我们的方式,所有表名都是小写的。(我们有一个MySQL选项集,它强制所有表名小写。)我们这样做是为了避免不同操作系统/文件系统(有些是区分大小写的,有些不是)
此外,表名是单数的。表的名称指定了表的一行所代表的内容。我们也不将\表
作为名称的一部分
MySQL中的列名从不区分大小写,但我们也总是使用小写作为列名。我们不使用“camelCase”我们的列名,我们使用下划线字符作为分隔符,例如,power\u id
vs.powerID
,hero\u name
vs.heroName
跟进
我上面的“注意事项”不是必须遵守的具体规则;这些只是我们使用的模式
遵循这些模式并不能保证我们会有一个成功的软件,但它确实帮助了我们
为了您的参考,我将展示这些桌子将如何作为我们商店的“第一次切割”,作为另一种模式的说明;这不是“正确的方式”,这只是我们作为一个团队已经确定的“方式”
CREATE TABLE superhero
( id INT UNSIGNED NOT NULL AUTO_INCREMENT COMMENT 'pk'
, hero_name VARCHAR(255) NOT NULL COMMENT ''
, first_name VARCHAR(255) NOT NULL DEFAULT '' COMMENT ''
, last_name VARCHAR(255) NOT NULL DEFAULT '' COMMENT ''
, first_appearance DATE COMMENT 'date superhero first appeared'
, gender ENUM('female','male','other') COMMENT 'female,male or other'
, biography_text TEXT COMMENT ''
, universe VARCHAR(255) COMMENT ''
, PRIMARY KEY(id)
, UNIQUE KEY superhero_UX1 (hero_name)
) ENGINE=InnoDB;
CREATE TABLE power
( id INT UNSIGNED NOT NULL AUTO_INCREMENT COMMENT 'pk'
, name VARCHAR(255) NOT NULL COMMENT ''
, description_text TEXT NOT NULL COMMENT ''
, PRIMARY KEY(id)
, UNIQUE KEY power_UX1 (name)
) ENGINE=InnoDB;
CREATE TABLE superheropower
( superhero_id INT UNSIGNED NOT NULL COMMENT 'pk, fk ref superhero'
, power_id INT UNSIGNED NOT NULL COMMENT 'pk, fk ref power'
, PRIMARY KEY(superhero_id, power_id)
, CONSTRAINT FK_superheropower_superhero
FOREIGN KEY(superhero_id) REFERENCES superhero(id)
ON UPDATE CASCADE ON DELETE CASCADE
, CONSTRAINT FK_superheropower_power
FOREIGN KEY (power_id) REFERENCES power(id)
ON UPDATE CASCADE ON DELETE CASCADE
) ENGINE=InnoDB;
您的设计似乎在正确的轨道上,这是我将使用的表-为字段添加一些索引,您可能会搜索并添加约束键所需的操作
CREATE TABLE `_superhero` (
`id` int(11) NOT NULL auto_increment,
`heroName` varchar(255) NOT NULL,
`firstName` varchar(255) default NULL,
`lastName` varchar(255) default NULL,
`firstAppearance` date default NULL,
`gender` enum('Other','Female','Male') default NULL,
`bio` text,
`universe` varchar(255) default NULL,
PRIMARY KEY (`id`),
KEY `indxHname` (`heroName`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
CREATE TABLE `_power` (
`id` int(11) NOT NULL auto_increment,
`name` varchar(255) NOT NULL,
`description` text NOT NULL,
PRIMARY KEY (`id`),
KEY `indx4` (`name`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
CREATE TABLE `_superheropower` (
`superheroID` int(11) NOT NULL default '0',
`powerID` int(11) NOT NULL default '0',
PRIMARY KEY (`superheroID`,`powerID`),
KEY `indx1` (`superheroID`),
KEY `indx2` (`powerID`),
CONSTRAINT `fk2` FOREIGN KEY (`powerID`) REFERENCES `_power` (`id`) ON DELETE CASCADE ON UPDATE NO ACTION,
CONSTRAINT `fk1` FOREIGN KEY (`superheroID`) REFERENCES `_superhero` (`id`) ON DELETE CASCADE ON UPDATE NO ACTION
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
找到答案的最简单方法是尝试一下,看看会发生什么:-)可能更适合于代码复查一些您称之为更正的内容只是首选项,其他则删除重要信息。此外,使用自动递增是一种常见的做法。@Gorilla:有几种不同的模式可以遵循。例如,有些人会反对使用代理id
列的模式。我们碰巧为实体表使用了代理整数主键,并使用id
作为列名。(我们的模式是有原因的。)我们所遵循的模式适合我们;我们的模式不是成功软件的唯一模式,它只是“适合”我们。作为另一个例子,我们将所有表名和列名都降为小写。没有规定说这是“正确”的方法。这只是我的团队遵循的一个指导原则。@spencer7593我完全理解,每个人都有自己的方式。像上面的代码一样,我使我更容易理解以及如何编写SQL语法。我还在学校学习计算机编程,所以我没有其他公司喜欢的工作经验,只是想说清楚。我包括的笔记只是我工作的一家特定商店的细节。这并不是说每个人都应该这样做。这只是关于我们这家店的几点说明;我通常只是指出我在我们店里看到的不同的东西。我们非常一致,遵循相当严格的模式和指导方针。大多数模式都有很好的理由,如果有很好的理由,也有偏离它们的空间。其他商店遵循不同的模式,更好地为他们工作,他们需要做什么。