如何检查CachedRowSet中是否存在列名?

我正在查询可能会发生变化的视图中的数据。 在我执行crs.get******()之前,我需要知道列是否存在。我发现我可以查询这样的元数据,以便在我从中请求数据之前查看列是否存在。

 ResultSetMetaData meta = crs.getMetaData(); int numCol = meta.getColumnCount(); for (int i = 1; i < numCol+1; i++) if(meta.getColumnName(i).equals("name")) return true; 

是否有更简单的方法来检查列是否存在?

编辑:它必须是数据库不可知的。 这就是我引用CachedRowSet而不是数据库的原因。

一般的JDBC API没有更简单的方法(至少不是我所知道的,或者可以找到……我在我自己开发的工具集中有完全相同的代码。)

(您的代码不完整):

 ResultSetMetaData meta = crs.getMetaData(); int numCol = meta.getColumnCount(); for (int i = 1; i < numCol+1; i++) { if(meta.getColumnName(i).equals("name")) {return true;} } return false; 

话虽这么说,如果您使用专有的,特定于数据库的API和/或SQL查询,我相信您可以找到更优雅的方法来做同样的事情......但是您必须为每个数据库编写自定义代码需要处理。 如果我是你,我会坚持使用JDBC API。

您提出的解决方案是否存在让您认为不正确的问题? 这对我来说似乎很简单......

如果列不在CachedRowSet中,你可以采用更短的方法来使用findColumn()为InvalidColumName抛出SQLException这一事实。

例如

  try { int foundColIndex = results.findColumn("nameOfColumn"); } catch { // do whatever else makes sense } 

可能是滥用exception处理(根据EffectiveJava第2版第57项),但它是循环遍历元数据中所有列的替代方法。

哪个数据库?

我认为在Oracle中列出了列的列表。

我不记得它是否适用于视图,但我猜他们这样做,它是这样的:

 select colum_name from all_views where view_name like 'myview' 

要么

 select name from all_objects where object_name like 'myview' and object_type='view' 

我不记得确切的语法。 你应该有空间权限。

每个RDBMS都应该有类似的东西。

您也可以执行查询

 select * from myView where 1 = 0 ; 

并且从元数据中获取列,如果您希望它在以前知道列是否存在之前避免获取数据。

不,真的没有更好的方法。 您可能想要重新查看问题。 如果您可以重新定义问题,有时它会使解决方案更简单,因为问题已经改变。

警告:以下评论纯粹来自内存而没有任何支持文书工作:)

如果我没记错的话,当oracle缓存的行集实现与连接池一起使用时,有一个神秘的问题会让它变得如此丑陋。 似乎存在对缓存的行集对象中保持的连接的静默引用(即使它应该断开连接),这将关闭随后在池中对垃圾收集打开的另一个连接。 出于这个原因,我最终放弃并编写了自己的数据对象层(这些天我将其交给spring和hibernate)。

旧线程,但我刚遇到同样的问题,最后得到了一个实用function:

 private Set getColumnNames(ResultSet cached) throws SQLException { ResultSetMetaData metaData = cached.getMetaData(); return IntStream.range(1, metaData.getColumnCount()) .mapToObj(i -> { try { return metaData.getColumnName(i); } catch (SQLException e) { throw new RuntimeException(e); } }).collect(toSet()); } 

如果我们不必在lambda中捕获exception(没有一些丑陋的黑客),这将是非常好的