インターフェイスの役割が混乱しているようですが、チュートリアルでは間違ったことがあります。インターフェイスRowMapper
およびRowCallbackHandler
は、値を提供する責任があります。行ごとに副作用を起こします。
したがって、それらは次の行に進むと、コールバックを呼び出すことではないの世話をするフレームワークとしてnext()
を呼び出すための責任を負うものではなく、一度next()
は、最初の行に進むときにも起こり得るfalse
を、返された場合にResultSet
は空です。後者の場合、query(… RowMapper<T>)
は、RowMapper
を呼び出さずに空のList
を返し、単にquery(… RowCallbackHandler)
は何もしません。対照的に
、ResultSetExtractor
適切next()
を呼び出す含む全体ResultSet
を処理する責任があります。だからあなたの質問の前提( "... の各呼び出しは私に新しい行を与えます。")が間違っています。すべてのJDBC操作の標準的な動作は、最初の行の前にあるResultSet
を返すことで、最初のnext()
呼び出しは現在の行ポインタを最初の行に移動するか、ResultSet
が空の場合はfalse
を返します。このソリューションはテストの結果、標準MySQL
とPostgresql
インスタンス/ Andremoniy /上で正常に動作します:あなたは最大1つの行を期待するのであれば、あなたのクエリは、むしろEDIT
return jdbcTemplate.query(sql, ps -> {
ps.setLong(1, fooParam1);
ps.setLong(2, fooParam2);
}, rs -> rs.next()? rs.getLong(1): null);
のようになります。 EDIT-2:このソリューションは、どこでも正しく動作し、正しく動作します。それがこの例で使用され、それは確かに、常にrs.getRows()
ため0
返す -
public <T> T query(String sql, PreparedStatementSetter pss, ResultSetExtractor<T> rse)
:しかし、それは、はJdbcTemplate
クラスに2つの異なる方法があることに気づいたでなければなりません。この場合、提供された解決策は正しいです。
jdbcTemplate.query(sql, ps -> { ps.setLong(1, fooParam1); ps.setLong(2, fooParam2); }, rs -> { System.out.println(rs.getRow()); });
異なる動作をします:rs.getRow()
処理行の数を返し、何行が存在しない場合、processRow
方法を別の3番目のパラメータの種類、及び同様のコードを有する
public void query(String sql, PreparedStatementSetter pss, RowCallbackHandler rch)
呼び出されることはありません(この2番目の方法は私の混乱の原因となります)。/Andremoniy/
なぜrs.hasNext()を使用しないのですか? –
@RadhakrishnaSharmaGorenta 'ResultSet'クラスにそのようなメソッドがありません – Andremoniy
もちろん、最初のパラメータ' sql'は既に 'next()'を呼び出す 'PreparedStatementCreator'実装である可能性がありますが、あなたの質問にコードを載せずにAPIに矛盾する何かを使っているときは、 'List'を返す' query'オーバーロードの1つで設定を試すことができます。最初の行が含まれているか不足していますか?すでに実証済みのように、Springは 'resultSetExtractor'の実装で' next() 'を呼び出します。 – Holger