Java 创建具有预填充信息的表时发生SQLITE数据库错误(表有3列,但提供了2个值)

Java 创建具有预填充信息的表时发生SQLITE数据库错误(表有3列,但提供了2个值),java,sqlite,Java,Sqlite,所以我刚刚开始使用Eclipse学习Java。我已经用它编写了一些Minecraft插件,但这是我为当地社区中心编写的第一个真正的桌面程序 这个程序需要使用一个数据库,所以我将使用一个本地数据库,而不是基于云的数据库,因为我刚刚进入这个领域 我已经在数据库上工作了一段时间,似乎无法克服以下错误:SQL错误或缺少数据库(table user有3列,但提供了2个值) 下面是我的代码和错误截图 提前感谢,, ~z~斯通 整个班级如下: package main; import java.sql.

所以我刚刚开始使用Eclipse学习Java。我已经用它编写了一些Minecraft插件,但这是我为当地社区中心编写的第一个真正的桌面程序

这个程序需要使用一个数据库,所以我将使用一个本地数据库,而不是基于云的数据库,因为我刚刚进入这个领域

我已经在数据库上工作了一段时间,似乎无法克服以下错误:SQL错误或缺少数据库(table user有3列,但提供了2个值)

下面是我的代码和错误截图

提前感谢,, ~z~斯通

整个班级如下:

package main;

import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;

public class SQLiteConnect {

private static Connection con;
private static boolean hasData = false;

public ResultSet displayUsers() throws ClassNotFoundException, SQLException {
    if (con == null) {
        getConnection();
    }

    Statement state = con.createStatement();
    ResultSet res = state.executeQuery("SELECT firstname, lastname FROM user");
    return res;
}

private void getConnection() throws ClassNotFoundException, SQLException {
    Class.forName("org.sqlite.JDBC");
    con = DriverManager.getConnection("jdbc:sqlite:SQLiteConnect.db");
    initialise();
}

private void initialise() throws SQLException {

    if ( !hasData) {
        hasData = true;

        Statement state = con.createStatement();
        ResultSet res = state.executeQuery("SELECT name FROM sqlite_master WHERE type='table' AND name='user'");

        if ( !res.next() ) {
            System.out.println("Building the User table with prepopulated values.");
            //need to build the table before you can call it if it doesn't already exist
            Statement state2 = con.createStatement();
            state2.execute("CREATE TABLE user(id integer," + "firstname varchar(60)," + "lastname varchar(60)," + "primary key(id));");

            // insert sample data
            PreparedStatement prep = con.prepareStatement("INSERT INTO user values(?,?);");
            prep.setString(1,  "John");
            prep.setString(2, "McNeil");
            prep.execute();

            PreparedStatement prep2 = con.prepareStatement("INSERT INTO user values(?,?);");
            prep2.setString(1,  "Paul");
            prep2.setString(2,  "Smith");
            prep2.execute();

        }

    }
}

public void addUser (String firstname, String lastname) throws ClassNotFoundException, SQLException {

    if (con == null) {
        getConnection();
    }

    PreparedStatement prep = con.prepareStatement("INSERT INTO user values(?,?);");
    prep.setString(1,  firstname);
    prep.setString(2,  lastname);
    prep.execute();

}
}

----------编辑1---------

好的,我将代码从第43行更改为:

state2.execute("CREATE TABLE user(id INTEGER AUTOINCREMENT," + "firstname varchar(60)," + "lastname varchar(60)," + "primary key(id));");
现在我得到了这个错误:“SQL错误或缺少数据库(靠近“自动增量”:语法错误)”

我可能只是没有按正确的顺序或其他什么输入

下图:


错误实际上说明了一切-表有三列,但插入时只提供其中两列。如果要这样做,需要显式列出要插入的列

另外,作为旁注,您不需要创建另一个
PreparedStatement
,但可以重用相同的语句:

PreparedStatement prep = 
    con.prepareStatement("INSERT INTO user (firstname, lastname) VALUES (?, ?;");

prep.setString(1, "John");
prep.setString(2, "McNeil");
prep.executeUpdate();

prep.setString(1, "Paul");
prep.setString(2, "Smith");
prep.executeUpdate();

如前所述,出现错误的原因是您要插入到一个有三列的表中,但存储过程只为两列提供值

您希望数据库为您提供id值。您的数据库可以做到这一点,如果您将表设置为这样做,那么您的存储过程就可以正常工作。您需要告诉数据库在用户表上自动递增(使用id值处的内部rowid)。这是作为数据库表定义的一部分通过添加INTEGER主键或INTEGER AUTOINCREMENT和ID列的数据类型来完成的

state2.execute("CREATE TABLE user(id integer," + "firstname varchar(60)," + "lastname varchar(60)," + "primary key(id));");
应该是

state2.execute("CREATE TABLE user(id INTEGER PRIMARY KEY," + "firstname varchar(60)," + "lastname varchar(60)," + "primary key(id));");


您的id缺少“自动增量”我是否只在“id整数”后面添加“自动增量”?是的,我知道,很抱歉我的问题表达得不够好。我真的很想知道:如何将我的表更改为只有两个插槽(一个用于名字,一个用于姓氏),或者为ID也设置一个插槽更好/更必要?我还以为我插入了三组信息:名字、姓氏和ID?在尝试了你的上述建议后,我发布了一个带有新错误的编辑,我还想让您知道,我试图按照他们在这里所说的做:但是在自动加入之前添加主键,或者在主键之后删除自动加入,都会导致一个错误,告诉我我的表有太多的主键。
state2.execute("CREATE TABLE user(id INTEGER AUTOINCREMENT," + "firstname varchar(60)," + "lastname varchar(60)," + "primary key(id));");