null安全な比較の書き方“< =>”純粋なSQLで?

StackOverflow https://stackoverflow.com/questions/802612

  •  03-07-2019
  •  | 
  •  

質問

Mysqlには、nullセーフである比較演算子< =>があります。次のような準備済みステートメントを作成するときに、Javaプログラムでこれを使用します。

String routerAddress = getSomeValue();
String sql = "SELECT * FROM ROUTERS WHERE ROUTER_ADDRESS <=> ? ";
PreparedStatement stmt = connection.prepareStatement(sql);
stmt.setString(1, routerAddress);

今、H2データベースに切り替えたいと思います。 &lt; =&gt;の書き方純粋なSQLの演算子(たとえば、IS NULLおよびIS NOT NULLを使用)? stmt.setString操作は 1回のみ使用したいです。列名を何度か書いても構いません。

関連する質問は、 SQLでnull == nullを取得です。しかし、その答えは、検索値が2回書き込まれることを必要とします(つまり、PreparedStatementで2つの疑問符)!?

リファレンス: http://dev.mysql.com/ doc / refman / 5.0 / en / comparison-operators.html#operator_equal-to

役に立ちましたか?

解決

  

関連する質問は、SQLでnull == nullを取得することです。しかし、その答えは、検索値が2回書き込まれることを必要とします(つまり、PreparedStatementで2つの疑問符)!?

2番目以降の回答は、検索値を2回バインドせずにこれを行う方法を示しています。

SELECT * FROM ROUTERS 
WHERE coalesce(ROUTER_ADDRESS, '') = coalesce( ?, '');

これには、有効な列値にはならないダミー値が必要であることに注意してください(これは「帯域外」です)。空の文字列を使用しています。そのような値がない場合は、値を2回バインドするのを我慢する必要があります。

SELECT * FROM ROUTERS 
WHERE ROUTER_ADDRESS = ? or (ROUTER_ADDRESS is null and ? is null);

他のヒント

SQLの標準のNULLセーフな等価演算子は、 IS DISTINCT FROM および IS NOT DISTINCT FROM です。

SQLでは、NULLはそれ自体と等しくありません。次のいずれかを実行できます。

1-次のように、ダミー値に置き換えて比較します。

SELECT * FROM ROUTERS WHERE ISNULL(ROUTER_ADDRESS,'xxx') <=> ISNULL(?,'xxx')

または

2-次のように、より複雑な論理テストに置き換えます:

SELECT *
FROM ROUTERS 
WHERE (
       (ROUTER_ADDRESS IS NULL AND ? IS NOT NULL)
       OR
       (ROUTER_ADDRESS IS NOT NULL AND ? IS NULL)
       OR
       (ROUTER_ADDRESS IS NOT NULL AND ? IS NOT NULL AND ROUTER_ADDRESS <> ?
      )

ROUTER_ADDRESSがnullであるROUTERSが必要な場合nullの場合、これはおそらく動作する可能性があります:

SELECT * 
FROM ROUTERS 
WHERE ROUTER_ADDRESS = (case when ROUTER_ADDRESS is null and ? is null then null 
                             else ? end)
ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top