VastbaseG100

基于openGauss内核开发的企业级关系型数据库。

Menu

执行SQL语句并处理结果

向数据库发出执行SQL的请求时,需要使用Statement或PreparedStatement,使用Statement或PrepareStatement实例发出查询,服务端执行完成后将返回一个ResultSet实例,该实例包括查询的结果。

执行查询

使用Statement执行查询

Statement st = conn.createStatement();
ResultSet rs = st.executeQuery("SELECT * FROM mytable WHERE columnfoo= 500");
while (rs.next())
{
System.out.print("Column 1 returned ");
System.out.println(rs.getString(1));
}
rs.close();

使用PreparedStatement执行查询

int foovalue = 500;
PreparedStatement st = conn.prepareStatement("SELECT * FROM mytable WHERE columnfoo = ?");
st.setInt(1, foovalue);
ResultSet rs = st.executeQuery();
while (rs.next())
{
System.out.print("Column 1 returned ");
System.out.println(rs.getString(1));
}
rs.close();
st.close();

使用游标获取结果

默认情况下,驱动程序将一次性获取查询的所有结果,当某个查询的结果集很庞大时,一次获取所有结果很不合理,因此JDBC驱动程序提供了一种基于数据库游标的ResultSet方法,只获取少量的行缓存在客户端。通过重新定位游标来获取下一批数据。

基于游标的ResultSet不能在所有情况下使用。有许多限制会使驱动程序一次性获取整个结果集:

  • 连接不能使用自动提交模式,因为后端会在事务结束时关闭游标,因此在自动提交模式下,事务结束后,在从游标获取数据之前,游标已经被关闭。

  • Statement必须使用ResultSet.TYPE_FORWARD_ONLY类型创建,这意味着不能在结果集中进行跳转或向后滚动。这也是默认值,因此不需要在代码中额外指定。

  • 给定的查询语句必须是单条语句,不能是用分号连接在一起的多个语句。

  • 必须设置fetch size,且fetch size不能为0。

示例:

// make sure autocommit is off
conn.setAutoCommit(false);
Statement st = conn.createStatement();

// Turn use of the cursor on.
st.setFetchSize(50);
ResultSet rs = st.executeQuery("SELECT * FROM mytable");
while (rs.next())
{
System.out.print("a row was returned.");
}
rs.close();

// Turn the cursor off.
st.setFetchSize(0);
rs = st.executeQuery("SELECT * FROM mytable");
while (rs.next())
{
System.out.print("many rows were returned.");
}
rs.close();

// Close the statement.
st.close();

使用Statement和 PreparedStatement接口

在使用Statement和PreparedStatement时,需要注意以下问题:

  • 可以多次使用一个Statement实例,可以在打开连接时创建Statement然后在连接的整个生命周期内使用它。但是必须注意在给定时间内每个Statement或PreparedStatement只能存在一个ResultSet.

  • 如果在处理ResultSet时需要执行查询,可以创建另一个Statement来执行。

  • 如果使用多线程,并且有多个线程正在使用数据库,则每个线程必须使用单独的Statement.

  • 使用完Statement或PreparedStatement应该及时关闭。

  • 在JDBC中,问号(?)是PreparedStatement的占位符,但是有一些操作符包含一个问号,为避免SQL语句中的问号被当成占位符,可以使用两个问号(??)进行转义。也可以在Statement中使用上述转义,但是不是必须的,因为在Statement中单个问号也可以用作操作符。

使用ResultSet接口

使用ResultSet接口时必须考虑下面的问题:

  • 在读取任何数值的时候,必须调用next(),如果还有结果则返回真(true)。

  • 在 JDBC 规范里,对一个字段应该只访问一次。遵循这个规则是最安全的,不过目前 Vastbase G100 JDBC驱动允许对一个字段访问任意次。

  • 在结束对一个 ResultSet 的处理后,必须调用 close()来关闭它。

  • 使用那个创建ResultSet的 Statement做另一个查询请求, 当前打开的ResultSet 实例将自动关闭。

执行更新

要更改数据(执行一个insert,update或者delete),可以使用 executeUpdate()方法. executeUpdate() 方法类似于发出 select语句的executeQuery()方法,不过,它不返回ResultSet,它返回的是insert,update或者delete语句影响的行数。

删除

int foovalue = 500;
PreparedStatement st = conn.prepareStatement("DELETE FROM mytable WHERE columnfoo = ?");
st.setInt(1, foovalue);
int rowsDeleted = st.executeUpdate();
System.out.println(rowsDeleted + " rows deleted");
st.close();

更新

int foovalue = 500;
PreparedStatement st = conn.prepareStatement("UPDATE mytable SET columninfo='updated' WHERE columnfoo = ?");
st.setInt(1, foovalue);
int rowsUpdated = st.executeUpdate();
System.out.println(rowsDeleted + " rows updated");
st.close();

插入

  • 插入单行:

    PreparedStatement st = conn.prepareStatement("INSERT INTO mytable(col_1,col_2) values(?,?)");
    st.setInt(1, 0);
    st.setString(2, "row1");
    int rowsInserted = st.executeUpdate();
    System.out.println(rowsDeleted + " rows inserted");
    st.close();
    
  • 插入多行:

    PreparedStatement st = conn.prepareStatement("INSERT INTO mytable(col_1,col_2) values(?,?)");
    st.setInt(1, 0);
    st.setString(2, "row1");
    st.addBatch();
    st.setInt(1,1);
    st.setString(2, "row2");
    st.addBatch();
    st.executeBatch();
    st.close();
    

创建或修改数据库对象

要创建、更改或者删除一个类似表或者视图这样的数据库对象, 可以使用execute() 方法, execute()方法类于发出 select语句的 executeQuery()方法,不过它不返回结果。

例如DROP表:

Statement st = conn.createStatement();
st.execute("DROP TABLE mytable");
st.close();