Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/mysql/70.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 用于创建表的MySQL Errno 150(不正确的外键)_Java_Mysql_Jdbc - Fatal编程技术网

Java 用于创建表的MySQL Errno 150(不正确的外键)

Java 用于创建表的MySQL Errno 150(不正确的外键),java,mysql,jdbc,Java,Mysql,Jdbc,我承认这已经被问了好几次了,我已经看过了很多答案 我知道errno150指的是外键不正确的表,我已经看到了前面的答案。我已经检查了那里的每一个条件,但无法解决这个问题。不知道我是否遗漏了一些明显的东西 这是使用MySQL的java实现,我有一个switch语句,它创建了两个表(目前),如下所示: 地址创建精细(无外键),患者给出错误150。相同的引擎、相同的字符集、相同的数据类型(甚至复制了一个粘贴的表以100%确定)、新创建的(空)表,都是非临时的 谢谢 另外,我不能使用显示引擎INNODB状

我承认这已经被问了好几次了,我已经看过了很多答案

我知道errno150指的是外键不正确的表,我已经看到了前面的答案。我已经检查了那里的每一个条件,但无法解决这个问题。不知道我是否遗漏了一些明显的东西

这是使用MySQL的java实现,我有一个switch语句,它创建了两个表(目前),如下所示:

地址创建精细(无外键),患者给出错误150。相同的引擎、相同的字符集、相同的数据类型(甚至复制了一个粘贴的表以100%确定)、新创建的(空)表,都是非临时的

谢谢

另外,我不能使用
显示引擎INNODB状态
,因为我没有足够高的权限级别

完整错误消息:

java.sql.SQLException: Can't create table 'team.Patient' (errno: 150)
    at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:964)
    at com.mysql.jdbc.MysqlIO.checkErrorPacket(MysqlIO.java:3970)
    at com.mysql.jdbc.MysqlIO.checkErrorPacket(MysqlIO.java:3906)
    at com.mysql.jdbc.MysqlIO.sendCommand(MysqlIO.java:2524)
    at com.mysql.jdbc.MysqlIO.sqlQueryDirect(MysqlIO.java:2677)
    at com.mysql.jdbc.ConnectionImpl.execSQL(ConnectionImpl.java:2545)
    at com.mysql.jdbc.StatementImpl.executeUpdateInternal(StatementImpl.java:1540)
    at com.mysql.jdbc.StatementImpl.executeLargeUpdate(StatementImpl.java:2595)
    at com.mysql.jdbc.StatementImpl.executeUpdate(StatementImpl.java:1468)
    at uk.team.App.makeTable(App.java:146)
    at uk.team.App.setupEnviro(App.java:80)
    at uk.team.App.access$1(App.java:45)
    at uk.team.App$1.run(App.java:33)
    at java.awt.event.InvocationEvent.dispatch(Unknown Source)
    at java.awt.EventQueue.dispatchEventImpl(Unknown Source)
    at java.awt.EventQueue.access$500(Unknown Source)
    at java.awt.EventQueue$3.run(Unknown Source)
    at java.awt.EventQueue$3.run(Unknown Source)
    at java.security.AccessController.doPrivileged(Native Method)
    at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(Unknown Source)
    at java.awt.EventQueue.dispatchEvent(Unknown Source)
    at java.awt.EventDispatchThread.pumpOneEventForFilters(Unknown Source)
    at java.awt.EventDispatchThread.pumpEventsForFilter(Unknown Source)
    at java.awt.EventDispatchThread.pumpEventsForHierarchy(Unknown Source)
    at java.awt.EventDispatchThread.pumpEvents(Unknown Source)
    at java.awt.EventDispatchThread.pumpEvents(Unknown Source)
    at java.awt.EventDispatchThread.run(Unknown Source)

由于Address表没有问题,因此这与Patient表的引用更相关,我假设team是数据库名称:

  • 根据我在这里看到的,引用的列应该被索引。您已经同时为这两个(
    houseNo
    postCode
    )创建了索引,为什么不尝试分别为它们创建索引,看看是否适合您

  • 尽管您已经提到您正在使用相同的引擎、字符集等,为什么不在上面的查询中明确地提到它们并运行它们呢。您能在查询中添加ENGINE=InnoDB吗

  • 如果对你不起作用,请告诉我

    所以我的答案(更多的是妥协)是:

    switch(tableName){
                case "Address":
                    stmt.executeUpdate("CREATE TABLE Address(houseID INT(8) NOT NULL PRIMARY KEY AUTO_INCREMENT, "
                            + "houseNo INT(4) NOT NULL, "
                            + "firstLine VARCHAR(30) NOT NULL, "
                            + "secondLine VARCHAR(30), "
                            + "city VARCHAR(25) NOT NULL, "
                            + "county VARCHAR(25) NOT NULL, "
                            + "postCode VARCHAR(7) NOT NULL)");
                    break;
                case "Patient":
                    stmt.executeUpdate("CREATE TABLE Patient(patientID INT(8) NOT NULL PRIMARY KEY AUTO_INCREMENT, "
                            + "title VARCHAR (10) NOT NULL, "
                            + "forename VARCHAR(15) NOT NULL, "
                            + "surname VARCHAR(25) NOT NULL, "
                            + "dob DATE NOT NULL, "
                            + "phoneNo CHAR(11) NOT NULL, "
                            + "houseID INT(8) NOT NULL, "
                            + "amountOwed DECIMAL(5,2) NOT NULL, "
                            + "FOREIGN KEY (houseID) REFERENCES Address (houseID))");
                    break;
    }
    

    在“Address”中创建一个附加字段,该字段的ID是“Patient”中的主键和唯一引用的外键。这并不理想,但很实用。

    如果要创建一个外键约束,使其与父表同一行中的两列匹配,则需要为两列指定一个外键(而不是为每列指定两个单独的FK约束)

    这对我来说适用于MySQL 5.6.13:

    stmt.executeUpdate(“创建表地址(houseNo INT(4)不为空,”
    +第一行VARCHAR(30)不为空
    +“第二行VARCHAR(30),”
    +city VARCHAR(25)不为空
    +county VARCHAR(25)不为空
    +邮政编码VARCHAR(7)不为空
    +“主键(房屋编号、邮政编码))”;
    stmt.executeUpdate(“创建表Patient(patientID INT(8)非空主键自动增量,”
    +title VARCHAR(10)不为空
    +forename VARCHAR(15)不为空
    +姓氏VARCHAR(25)不为空
    +dob日期不为空
    +phoneNo字符(11)不为空
    +houseNo INT(4)不为空
    +邮政编码VARCHAR(7)不为空
    +未计数的十进制数(5,2)不为空
    +“外键(门牌号,邮政编码)参考地址(门牌号,邮政编码))”;
    
    您能粘贴整个错误吗?你在mysql命令行上得到了什么?@ShivaShinde它是通过Java创建的,我可以在原始帖子中添加完整的错误。请添加完整的错误@ShivaShinde doneThanks谢谢你的帮助。在尝试了你的建议之后(不幸的是,这两个建议都不起作用)。我决定妥协,在地址表中添加一个自动生成的ID,作为患者的单键主键和外键。我将把它作为一个答案发布(尽管我很清楚它不是真的)。再次感谢。
    switch(tableName){
                case "Address":
                    stmt.executeUpdate("CREATE TABLE Address(houseID INT(8) NOT NULL PRIMARY KEY AUTO_INCREMENT, "
                            + "houseNo INT(4) NOT NULL, "
                            + "firstLine VARCHAR(30) NOT NULL, "
                            + "secondLine VARCHAR(30), "
                            + "city VARCHAR(25) NOT NULL, "
                            + "county VARCHAR(25) NOT NULL, "
                            + "postCode VARCHAR(7) NOT NULL)");
                    break;
                case "Patient":
                    stmt.executeUpdate("CREATE TABLE Patient(patientID INT(8) NOT NULL PRIMARY KEY AUTO_INCREMENT, "
                            + "title VARCHAR (10) NOT NULL, "
                            + "forename VARCHAR(15) NOT NULL, "
                            + "surname VARCHAR(25) NOT NULL, "
                            + "dob DATE NOT NULL, "
                            + "phoneNo CHAR(11) NOT NULL, "
                            + "houseID INT(8) NOT NULL, "
                            + "amountOwed DECIMAL(5,2) NOT NULL, "
                            + "FOREIGN KEY (houseID) REFERENCES Address (houseID))");
                    break;
    }