【问题标题】:How To determine the ResultSet Column type dynamically如何动态确定 ResultSet 列类型
【发布时间】:2016-08-12 14:00:13
【问题描述】:

我需要在运行时为 DB 中的所有表动态生成一个 INSERT stmt。我正在逐一获取表内容(数据)并在运行时确定列类型,同时通过 ResultSet 和 ResultSetMetaData 循环,以便为字符串类型添加双引号(“)而不为非字符串类型的列添加相同的. 然而,随着当前逻辑的实现,它忽略了第一条记录,并且对表中的所有剩余记录都工作得很好。我知道它为什么工作,因为在获取rs.getColumnType(int columnIndex) 时,我们需要给出从 1 个索引开始的列名..但无法构建逻辑,以便它也会检查第一行而不是此时忽略它..

请看下面的代码sn-p

if (rs != null) {
    while (rs.next()) {
        sqlString = new StringBuffer();

        for (int i = 1; i <= columnCount; i++) {
            Object obj = rs.getObject(i);

            if (obj == null) {
                sqlString.append("null");
                sqlString.append(",");
            }
            else
            {
                int sqlTypes = rsmd.getColumnType(i);

                switch (sqlTypes) {
                    case Types.VARCHAR:
                        sqlString.append("\"");
                        if (obj != null)
                            sqlString.append(rs.getString(i));

                        sqlString.append("\"");
                        sqlString.append(",");
                        break;
                    case Types.NULL:
                        sqlString.append("null");
                        sqlString.append(",");
                        break;
                    case Types.CHAR:
                        sqlString.append("\"");
                        if (obj != null)
                            sqlString.append(rs.getString(i));

                        sqlString.append("\"");
                        sqlString.append(",");
                        break;
                    case Types.TIMESTAMP:
                        sqlString.append("\"");
                        if (obj != null)
                            sqlString.append(rs.getTimestamp(i));

                        sqlString.append("\"");
                        sqlString.append(",");
                        break;
                    case Types.DOUBLE:
                        if (obj != null)
                            sqlString.append(rs.getDouble(i));

                        sqlString.append(",");
                        break;
                    case Types.INTEGER:
                        if (obj != null)
                            sqlString.append(rs.getInt(i));

                        sqlString.append(",");
                        break;
                    case Types.SMALLINT:
                        if (obj != null)
                            sqlString.append(rs.getInt(i));

                        sqlString.append(",");
                        break;
                    case Types.DECIMAL:
                        if (obj != null)
                            sqlString.append(rs.getBigDecimal(i));

                        sqlString.append(",");
                        break;

                    /*default:
                        if (obj != null)
                            sqlString.append(obj.toString());

                        sqlString.append(",");
                        break;*/
                }
            }
        }

【问题讨论】:

  • 为什么要遍历所有行? "while (rs.next())" 您只需获取 ResultSetMetaData 一次!每一行都将具有完全相同的元数据。你不需要调用“rs.next()”
  • 同意,但我需要遍历所有行,因为我还需要获取数据来为该行生成一个 INSERT stmt,因此 rs.next(),不确定这是否能回答你的问题查询
  • 如果我理解正确,那么您的任务就是从 mysql 数据库中导出数据。有一些工具可以比您自己的程序做得更好。当您的导出运行时数据发生变化时,请考虑问题。特别是当一个表引用另一个表时。我会寻找合适的工具来完成导出工作。
  • 这需要通过应用程序进程中的Java代码以编程方式生成以实现某些要求,因此这种实现:)
  • 只需拨打rs.getSomething(i-1)即可。

标签: java resultset


【解决方案1】:

您是否尝试过像这样使用 do while 循环:

if (rs != null) {
  do{
    sqlString = new StringBuffer();

    for (int i = 1; i <= columnCount; i++) {
        Object obj = rs.getObject(i);

        if (obj == null) {
            sqlString.append("null");
            sqlString.append(",");
        }
        else
        {
            int sqlTypes = rsmd.getColumnType(i);

            switch (sqlTypes) {
                case Types.VARCHAR:
                    sqlString.append("\"");
                    if (obj != null)
                        sqlString.append(rs.getString(i));

                    sqlString.append("\"");
                    sqlString.append(",");
                    break;
                case Types.NULL:
                    sqlString.append("null");
                    sqlString.append(",");
                    break;
                case Types.CHAR:
                    sqlString.append("\"");
                    if (obj != null)
                        sqlString.append(rs.getString(i));

                    sqlString.append("\"");
                    sqlString.append(",");
                    break;
                case Types.TIMESTAMP:
                    sqlString.append("\"");
                    if (obj != null)
                        sqlString.append(rs.getTimestamp(i));

                    sqlString.append("\"");
                    sqlString.append(",");
                    break;
                case Types.DOUBLE:
                    if (obj != null)
                        sqlString.append(rs.getDouble(i));

                    sqlString.append(",");
                    break;
                case Types.INTEGER:
                    if (obj != null)
                        sqlString.append(rs.getInt(i));

                    sqlString.append(",");
                    break;
                case Types.SMALLINT:
                    if (obj != null)
                        sqlString.append(rs.getInt(i));

                    sqlString.append(",");
                    break;
                case Types.DECIMAL:
                    if (obj != null)
                        sqlString.append(rs.getBigDecimal(i));

                    sqlString.append(",");
                    break;

                /*default:
                    if (obj != null)
                        sqlString.append(obj.toString());

                    sqlString.append(",");
                    break;*/
            }
        }while (rs.next());
    }

【讨论】:

  • 不。它引发了相同的错误,即列索引超出范围,0
  • 抱歉以上评论,它工作得很好。欣赏!!
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-04-05
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多