問題は、SQLite が引数をエスケープし、クエリ文字列"1,2,3"
の単一のプレースホルダーを置き換えるために使用される単一の値に変換することです。?
複数の引数を指定する正しい方法は、個々の引数ごとにプレースホルダーを用意することです。元のコード行を次のように変更する必要があります。
findWithQuery(A.class, "SELECT * FROM <table> WHERE <column> in (?,?,?)", new String[] { "1","2","3" })
後で、引数の数が動的であることを指摘しました。これは、クエリを実行する引数に基づいて実行時にクエリ (特に where 句) を生成することで簡単に実現できます。
最も一般的なケースでは、これを行うのに数行のコードしか必要ありません。
final String[] args = new String[] { /* ... */ };
final String query = "SELECT * FROM <table> WHERE <column> in " +
"(" + TextUtils.join(",", Collections.nCopies(args.length, "?")) + ")";
final List<A> result = A.findWithQuery(A.class, query, args);
(ショートカットを使用して、プレースホルダーを使用する代わりに、引数をクエリ文字列に直接挿入できることに注意してください。ただし、SQLiteの組み込みのエスケープが失われるため、これに反対することにしました)
あとはString[]
、引数から out を生成するだけです。このような単純なヘルパー メソッドは、ほとんどのシナリオをカバーする必要があります。
static String[] toStringArray(Object... args) {
final String[] array = new String[args.length];
for (int i = 0; i < args.length; i++) array[i] = args[i].toString();
return array;
}
null
プリミティブ配列を引数として使用する予定がある場合は、おそらくそこにいくつかのチェックを追加し、潜在的にいくつかのオーバーロードを設定する必要があります。
免責事項: すべてをブラウザーに直接入力したため、すべてが機能することを保証するものではなく、最初の試みです。:)