我有三组对象都在同一个Realm数据库中。每个组都是一组标签和其他信息,对于每个标签,我必须向网络请求接收id。每个组的查询都不同(URL更改和响应)。
有必要并行地为每个组发出请求,每分钟不超过20个查询。即使活动被破坏,该计划也应该有效。我做了IntentServie,但下一步我不知道应该做什么。如何正确地进行延迟的并行查询?是否可以使用IntentService?
循环"对于"显示更好地理解问题。此外,所有响应都应写在一个数据库中,这就是所有流都必须可以访问的原因。
public class SubscribersGathering extends IntentService {
private RealmResults<HashtagObject> hashtags;
private RealmResults<SearchtagObject> searchtags;
private RealmResults<NametagObject> nametags;
public SubscribersGathering() {
super("SubscribersGathering");
}
@Override
protected void onHandleIntent(Intent intent) {
Realm realmForThisThread = Realm.getDefaultInstance();
this.hashtags = realmForThisThread.where(HashtagObject.class).findAll();
this.searchtags = realmForThisThread.where(SearchtagObject.class).findAll();
this.nametags = realmForThisThread.where(NametagObject.class).findAll();
realmForThisThread.close();
for(int i=0;i<hashtags.size();i++){
getHashtagTag(hashtags.get(i).getHashtag());
}
for(int i=0;i< searchtags.size();i++){
getSearchTags(searchtags.get(i).getId());
}
etc
}
private void getHashtagTag(final String tagName){
HttpURLConnection urlConnection = null;
try {
URL url = new URL(“URL_1”);
urlConnection = (HttpURLConnection) url
.openConnection();
urlConnection.setRequestMethod("GET");
urlConnection.setDoInput(true);
urlConnection.connect();
String response = Tools.streamToString(urlConnection
.getInputStream());
JSONObject jsonObj = (JSONObject) new JSONTokener(response)
.nextValue();
for(int i=0;i<jsonObj.getJSONArray("data").length();i++) {
JSONObject json = (JSONObject) jsonObj.getJSONArray("data").get(i);
Log.d(tagName, json.getJSONObject("user").getString("id"));
}
}catch(Exception exc){
exc.printStackTrace();
}finally {
if(urlConnection!=null){
try{
urlConnection.disconnect();
}catch(Exception e){
e.printStackTrace();
}
}
}
}
private void getSearchTags (final String tagName){
}
etc
}
答案 0 :(得分:1)
您有很多选项可以执行并行运行的网络操作。它取决于你选择什么。基本上,我可以建议你其中一个:
将任务拆分为runnables并使用ExecutorService运行它们。代码可能如下所示:
public void onHandleIntent(Intent intent) {
Runnable hashtagsTask = new Runnable() {
@Override
public void run() {
for (int i = 0; i < hashtags.size(); i++) {
getHashtag(i);// do something, fetch hashtags, etc
}
}
};
Runnable searchtagsTask = new Runnable() {
@Override
public void run() {
// do something
}
};
ExecutorService pool = Executors.newFixedThreadPool(3);
pool.execute(hashtagsTask);
pool.execute(searchtagsTask);
// etc
pool.awaitTermination();
}
将您的任务拆分为多个IntentServices。所以每个服务都会获取自己的数据。我个人认为这不是一个好的解决方案,但在某些情况下它可能是灵活的。
使用RxJava及其Observable#zip方法。这里的关键思想是将每个observable订阅到自己的线程:
public void onHandleIntent(Intent intent) {
Observable.zip(
getHashtags().subscribeOn(Schedulers.newThread()),
getSearchtags().subscribeOn(Schedulers.newThread()),
new Func2<List<String>, List<String>, Void>() {
@Override
public Void call(List<String> hashtags, List<String> searchtags) {
// do something with your data
return null;
}
}
)
.subscribe();
}
private Observable<List<String>> getHashtags() {
return Observable.defer(new Func0<Observable<List<String>>>() {
@Override
public Observable<List<String>> call() {
// fetch your data
return null;
}
};
}