针对单表数据量过大的场景,分页查询必不可少。针对sybase数据库分页查询的案例全网稀少,特别是指定起始页的分页查询实现。
本文依靠实际开发场景,特此总结Sybase数据库分页查询(指定起始位置)。
一、 SQL实现分页查询(指定起始页)
1. 查看表数据
2. 创建临时表
3. 临时表中分页查询,升序
4. 删除临时表(建议删除,避免资源占用)
二、代码实现 (指定起始页)
/**
* sybase暂无合适的分页方案,全查
* @param dataBaseName 数据库名称
* @param schemaName schema名称
* @param tableName 表名称
* @param sortingField 排序字段,主键或者索引字段
* @param connection 数据库连接
* @param startPosition 每一页的起始查询位置
* @param singlePageLength 每页获取多少条数据
* @return
* @throws Exception
*/
public Map<String, JSONObject> pagingQuerySample(String dataBaseName, String schemaName, String tableName,
String sortingField, Object connection, long startPosition, Integer singlePageLength) throws Exception{
String sqlOne = "";
String sqlTwo = "";
String sqlThree = "";
ResultSet rs = null;
PreparedStatement preStmt = null;
Map<String, JSONObject> resultMap = null;
try{
// sybase不支持复杂子查询,需拆分两步
// 创建临时表#delTmp_tb,复制原始表数据并新增字段dlprownum
sqlOne = String.format("select * , dlprownum=identity(10) into #delTmp_tb from %s.[%s]",schemaName, tableName);
((Connection)connection).prepareStatement(sqlOne).executeUpdate();
// 临时表中分页查询,升序
sqlTwo = String.format("select * from #delTmp_tb where dlprownum between %s and %s order by dlprownum ASC",startPosition, startPosition+singlePageLength - 1);
preStmt = ((Connection)connection).prepareStatement(sqlTwo, ResultSet.TYPE_SCROLL_INSENSITIVE,
ResultSet.CONCUR_READ_ONLY);
// 组装结果
rs = preStmt.executeQuery();
resultMap = ResultSetUtil.getMapResultSetForSybase(rs);
// 删除临时表
sqlThree = String.format("DROP TABLE #delTmp_tb");
((Connection)connection).prepareStatement(sqlThree).executeUpdate();
}catch (Exception e){
e.printStackTrace();
LOGGER.error("分页查询数据失败,失败原因是:", e);
}finally {
// 关闭资源
try {
if (rs != null) {
rs.close();
}
if (preStmt != null) {
preStmt.close();
}
} catch (SQLException e) {
e.printStackTrace();
}
}
return resultMap;
}
/**
* 组装Sybase分页查询结果
* @param rs 分页查询结果
* @return SQLResultSet
*/
public static Map<String, JSONObject> getMapResultSetForSybase(ResultSet rs)
{
try {
Map<String, JSONObject> resultMap = new HashMap<>(16);
if(null==rs){
return resultMap;
}
ResultSetMetaData resultMetaData = rs.getMetaData();
List<JSONObject> columnJsonList = new ArrayList<>();
int size = resultMetaData.getColumnCount();
//TODO 获取所有列名称
for(int i=1;i<=size;i++) {
JSONObject jsonObject = new JSONObject(2);
jsonObject.put("columnName",resultMetaData.getColumnName(i));
jsonObject.put("columnType",resultMetaData.getColumnTypeName(i));
columnJsonList.add(jsonObject);
}
for (JSONObject jsonObject : columnJsonList) {
if (null != jsonObject){
String columnName = jsonObject.getString("columnName");
String columnType = jsonObject.getString("columnType");
if (StringUtil.isEmpty(columnName) || StringUtil.isEmpty(columnType)){
continue;
}
// 针对特殊类型的字段不进行处理
if (columnType.toLowerCase().contains("blob") || columnType.toLowerCase().contains("clob")
|| columnType.toLowerCase().contains("long varchar") || columnType.toLowerCase().contains("long vargraphic")
|| columnType.toLowerCase().contains("numeric")){
continue;
}
JSONObject resultJson = new JSONObject(2);
List<String> columnValues = new ArrayList<>();
while(rs.next()) {
try {
String columnValue = rs.getString(columnName);
if (StringUtil.isNotEmpty(columnValue)){
columnValues.add(columnValue);
}
} catch (Throwable ignored) {
}
}
resultJson.put("columnSize",columnValues.size());
resultJson.put("columnData",columnValues);
resultMap.put(columnName,resultJson);
//TODO 游标置位
rs.beforeFirst();
}
}
return resultMap;
} catch (Exception e) {
e.printStackTrace();
return null;
}
}