我们如何使用 google 融合表执行批量 SQL SELECT?
How we can perform bulk SQL SELECT with google fusion tables?
我有 ROWID 列表,想要获取具有此类 ID 的行。所以我这样做:
for (Integer id : duplicateIds) {
String sqlQuery = "SELECT ROWID, date, containerId FROM " + TABLE + " WHERE ROWID = '" + id + "'";
Fusiontables.Query.Sql sql = db.query().sql(sqlQuery);
List<List<Object>> row = sql.execute().getRows();
allRows.addAll(row);
}
但是duplicateIds列表的大小不小,我认为这种方法不好,因为做SQL查询很费时间。
所以,我想知道是否有可能执行类似批量查询的操作,或者是否存在另一种方法?怎么做更有效率?
更新。我发现有这样的东西的批量请求。但我仍然不知道如何去做并得到 List> 类型对象的响应。
提前致谢。
下面是如何对融合表执行批量 API 请求的示例。您应该注意,每个用户每 100 秒的请求有配额,我使用 Thread.sleep(TIME) 函数来避免错误。
private static List<List<Object>> buildRows(Fusiontables db, Set<String> rowIds, List<List<Object>> allRows)
throws Exception {
BatchRequest batchRequest = db.batch();
int c = 1;
BatchCallback<Sqlresponse, GoogleJsonErrorContainer> batchCallback = getBatchCallback(allRows);
for (String id : rowIds) {
String sqlQuery = "SELECT * FROM " + TABLE_ID + " WHERE ROWID = '" + id + "'";
HttpRequest request = db.query().sqlGet(sqlQuery).buildHttpRequest();
batchRequest.queue(request, Sqlresponse.class, GoogleJsonErrorContainer.class, batchCallback);
c++;
if (c == 200) {
batchRequest.execute();
Thread.sleep(REQUEST_QUOTAS_LIMIT);
}
}
private static BatchCallback<Sqlresponse, GoogleJsonErrorContainer> getBatchCallback(final List<List<Object>> out) {
return new BatchCallback<Sqlresponse, GoogleJsonErrorContainer>() {
@Override
public void onSuccess(Sqlresponse sqlresponse, HttpHeaders httpHeaders) throws IOException {
out.addAll(sqlresponse.getRows());
}
@Override
public void onFailure(GoogleJsonErrorContainer googleJsonErrorContainer, HttpHeaders httpHeaders) throws IOException {
System.err.println("Batching fails");
System.err.println(googleJsonErrorContainer.getError());
}
};
}
这是一个更好的解决方案。您可以创建一个 single SELECT 查询来检索您需要的数据,而无需批处理多个SELECT 查询。您只需要构建查询以使用 IN 子句。
首先,获取您的 dulplicateIds
数组并将其转换为字符串,注意删除左括号和右括号:
// Get id array as string and remove opening and closing brackets '[' & ']'
String idsAsString = duplicateIds.toString().replaceAll("\[|\]", "");
然后使用 IN 子句编写您的查询。
// Build Query
String sqlQuery = 'SELECT * FROM ' + TABLE_ID + ' WHERE ROWID IN (\"' + idsAsString + '\")';
Fusion Tables 的 SQL API 没有实现完整的 SQL 标准,但它仍然非常强大。在以下 link:
查看 SELECT 查询的文档
https://developers.google.com/fusiontables/docs/v2/sql-reference#Select
列出了一些您将来可能会觉得有用的其他条款。
我有 ROWID 列表,想要获取具有此类 ID 的行。所以我这样做:
for (Integer id : duplicateIds) {
String sqlQuery = "SELECT ROWID, date, containerId FROM " + TABLE + " WHERE ROWID = '" + id + "'";
Fusiontables.Query.Sql sql = db.query().sql(sqlQuery);
List<List<Object>> row = sql.execute().getRows();
allRows.addAll(row);
}
但是duplicateIds列表的大小不小,我认为这种方法不好,因为做SQL查询很费时间。 所以,我想知道是否有可能执行类似批量查询的操作,或者是否存在另一种方法?怎么做更有效率?
更新。我发现有这样的东西的批量请求。但我仍然不知道如何去做并得到 List> 类型对象的响应。
提前致谢。
下面是如何对融合表执行批量 API 请求的示例。您应该注意,每个用户每 100 秒的请求有配额,我使用 Thread.sleep(TIME) 函数来避免错误。
private static List<List<Object>> buildRows(Fusiontables db, Set<String> rowIds, List<List<Object>> allRows)
throws Exception {
BatchRequest batchRequest = db.batch();
int c = 1;
BatchCallback<Sqlresponse, GoogleJsonErrorContainer> batchCallback = getBatchCallback(allRows);
for (String id : rowIds) {
String sqlQuery = "SELECT * FROM " + TABLE_ID + " WHERE ROWID = '" + id + "'";
HttpRequest request = db.query().sqlGet(sqlQuery).buildHttpRequest();
batchRequest.queue(request, Sqlresponse.class, GoogleJsonErrorContainer.class, batchCallback);
c++;
if (c == 200) {
batchRequest.execute();
Thread.sleep(REQUEST_QUOTAS_LIMIT);
}
}
private static BatchCallback<Sqlresponse, GoogleJsonErrorContainer> getBatchCallback(final List<List<Object>> out) {
return new BatchCallback<Sqlresponse, GoogleJsonErrorContainer>() {
@Override
public void onSuccess(Sqlresponse sqlresponse, HttpHeaders httpHeaders) throws IOException {
out.addAll(sqlresponse.getRows());
}
@Override
public void onFailure(GoogleJsonErrorContainer googleJsonErrorContainer, HttpHeaders httpHeaders) throws IOException {
System.err.println("Batching fails");
System.err.println(googleJsonErrorContainer.getError());
}
};
}
这是一个更好的解决方案。您可以创建一个 single SELECT 查询来检索您需要的数据,而无需批处理多个SELECT 查询。您只需要构建查询以使用 IN 子句。
首先,获取您的 dulplicateIds
数组并将其转换为字符串,注意删除左括号和右括号:
// Get id array as string and remove opening and closing brackets '[' & ']'
String idsAsString = duplicateIds.toString().replaceAll("\[|\]", "");
然后使用 IN 子句编写您的查询。
// Build Query
String sqlQuery = 'SELECT * FROM ' + TABLE_ID + ' WHERE ROWID IN (\"' + idsAsString + '\")';
Fusion Tables 的 SQL API 没有实现完整的 SQL 标准,但它仍然非常强大。在以下 link:
查看 SELECT 查询的文档https://developers.google.com/fusiontables/docs/v2/sql-reference#Select
列出了一些您将来可能会觉得有用的其他条款。