我有以下代码......
protected long getNumQueuedChunks(boolean distinctEntries) throws Exception {
SQLiteDatabase db = null;
try {
db = dbhelper.getReadableDatabase();
String whereClause = C_STATUS + " = ? AND " + C_NUM_FAILURES + " < ?";
String[] whereArgs = new String[] {STATUS_AWAITING_PROCESSING, 10};
long count = DatabaseUtils.queryNumEntries(db, QUEUE_TABLE_NAME, whereClause, whereArgs);
return count;
}
finally {
try {
db.close();
}
catch(Exception ignore) {
}
}
}
...如果我想返回与WHERE条件匹配的行总数,它可以正常工作。
但是,我想只计算在这3列中具有不同/唯一数据组合的记录:C_URI,C_BYTE_START_NUM和C_NUM_BYTES。
我知道我可以做点像......
String[] columns = {C_URI, C_BYTE_START_NUM, C_NUM_BYTES};
String whereClause = C_STATUS + " = ? AND " + C_NUM_FAILURES + " < ?";
String[] whereArgs = new String[] {STATUS_AWAITING_PROCESSING, "10"};
Cursor c = db.query(true, QUEUE_TABLE_NAME, columns, whereClause, whereArgs, null, null, null, null);
int count = c.getCount();
...但我希望在这种情况下有一种更有效的方法来执行一个独特的计数?
只是为了增加清晰度,如果我在表格中有这些数据......
C_URI | C_BYTE_START_NUM | C_NUM_BYTES
1.jpg | 0 | 1024
1.jpg | 1024 | 1999年
2.jpg | 0 | 500
2.jpg | 0 | 500
...非重复计数的结果应为3。
注意 - 我已经看到了here (second answer)所描述的类似要求,但这对我没有帮助,因为我想要对3列进行不同的计数,而不只是一个。
答案 0 :(得分:4)
计算记录的最有效方法是让数据库执行此操作:
SELECT COUNT(*)
FROM (SELECT DISTINCT Uri,
ByteStartNum,
NumBytes
FROM QueueTable)
(使用单独的子查询,如果在三列上使用DISTINCT或GROUP BY,则无关紧要。)
此查询不适合其中一个辅助函数(如query
或queryNumEntries
)的约束,因此您必须手动构造整个SQL语句:
long getNumQueuedChunks() {
SQLiteDatabase db = dbhelper.getReadableDatabase();
try {
String query = "SELECT COUNT(*) FROM " +
"(SELECT DISTINCT " + C_URI + "," + C_BYTE_START_NUM + "," + C_NUM_BYTES +
" FROM " + QUEUE_TABLE_NAME +
" WHERE " + C_STATUS + " = ?" +
" AND " + C_NUM_FAILURES + " < 10)";
String[] args = new String[] { STATUS_AWAITING_PROCESSING };
return DatabaseUtils.longForQuery(db, query, args);
} finally {
db.close();
}
}
答案 1 :(得分:1)
您是否尝试过SQLiteDatabase.rawQuery()方法?您可以在其中放置原始SQL查询,例如:
select distinct C_URI, C_BYTE_START_NUM, C_NUM_BYTES from MyTable
该方法返回一个Cursor,您可以立即从游标对象获取计数。当然,如果您愿意,也可以指定where子句。然后在计算完毕后释放光标。