You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

JDBC插入数据报错:列位置超出范围问题排查与修复

问题分析与修复方案

你遇到的这个错误核心原因非常明确:你把要插入的ID值a当成了PreparedStatement的参数位置索引,而不是设置到第一个占位符?的实际值。

PreparedStatement的setXxx系列方法(比如setInt、setString)的第一个参数是占位符的位置(从1开始计数),而不是列的具体值。你现在写的myStmt.setString(a , firstName),当输入的a=45时,程序会去寻找SQL语句里的第45个占位符,但你的SQL只有2个?,自然就抛出了列位置越界的错误。


修复步骤

  • 修正参数设置逻辑:SQL里第一个?对应ID列,第二个对应Name列,所以要用setInt(1, a)设置ID值,setString(2, firstName)设置Name值。
  • 合并Scanner对象:你同时创建了两个Scanner实例,会导致输入读取异常(比如读取完整数后,换行符会被第二个Scanner读取,导致Name输入直接为空),只保留一个即可。
  • 补充驱动加载(规范优化):虽然部分JDBC驱动会自动加载,但显式加载驱动能让代码更健壮。

修正后的完整代码

package Rdbms;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.SQLException;
import java.util.Scanner;

class Jdbcfrnd { 
    public static void main(String[] args) throws SQLException { 
        String drv = "org.apache.derby.jdbc.ClientDriver";
        String url = "jdbc:derby://localhost:1527/Oracle;create=true;";
        String user = "Android";
        String password = "java";
        Connection myConn = null;
        PreparedStatement myStmt = null;
        Scanner scanner = null;

        try { 
            // 显式加载JDBC驱动
            Class.forName(drv);
            scanner = new Scanner(System.in);

            System.out.print("Enter ID number: ");
            int a = scanner.nextInt();
            // 消耗nextInt后遗留的换行符,避免后续nextLine读取空字符串
            scanner.nextLine();
            
            System.out.print("Enter your Name: ");
            String firstName = scanner.nextLine();

            myConn = DriverManager.getConnection(url, user, password);
            String sql = "insert into GOOD (ID, Name) values (?, ?)";
            myStmt = myConn.prepareStatement(sql);
            
            // 按占位符顺序设置值:1对应ID,2对应Name
            myStmt.setInt(1, a);
            myStmt.setString(2, firstName);
            
            myStmt.executeUpdate();
            System.out.println("Insert complete.");
        } catch (Exception exc) { 
            exc.printStackTrace();
        } finally { 
            // 优化资源关闭的异常处理
            try {
                if (myStmt != null) myStmt.close();
                if (myConn != null) myConn.close();
                if (scanner != null) scanner.close();
            } catch (SQLException e) {
                e.printStackTrace();
            }
        }
    }
}

关键注意点

  • 占位符索引规则:PreparedStatement的占位符从1开始计数,和SQL中?出现的顺序一一对应,绝对不能和要插入的列值混淆。
  • Scanner输入的坑:nextInt()只会读取整数内容,不会处理输入后的换行符,必须调用nextLine()消耗掉这个换行符,否则后续的nextLine()会直接读取到空字符串。
  • 资源关闭优化:如果使用Java 7及以上版本,推荐用try-with-resources语法自动关闭资源,能避免手动关闭时的异常遗漏问题。

内容的提问来源于stack exchange,提问作者four systems

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.15 06:37:00