使用volley库,在onResponse方法中,ArrayList有一些数据,但在OnResponse方法之外,arraylist是空的 [英] Using volley library, inside the onResponse Method the ArrayList have some data but outside the OnResponse method the arraylist is empty
问题描述
我正在模型中进行网络操作,然后返回结果,但是当我返回时,arraylist大小为零但是在 onResponse
方法中,arraylist大小为不是零。如何解决这个问题?
I am doing the network operation in a model and then return the result, but the arraylist size is zero when I return it but inside the onResponse
method the arraylist size is not zero. How to resolve this?
public class doInBackground {
//i have initialized the arraylist here
ArrayList<Contact> arrayList=new ArrayList<>();
String url="http://192.168.10.3/volley/allUser.php";
private Context context;
public doInBackground(Context context){
this.context=context;
}
public ArrayList<Contact> getArrayList(){
JsonArrayRequest jsonArrayRequest=new JsonArrayRequest(Request.Method.POST, url, null, new Response.Listener<JSONArray>() {
@Override
public void onResponse(JSONArray response) {
for(int i=0;i<response.length();i++){
try {
JSONObject jsonObject=response.getJSONObject(i);
Contact contact=new Contact();
contact.setName(jsonObject.getString("name"));
contact.setUserName(jsonObject.getString("username"));
arrayList.add(contact);
} catch (JSONException e) {
e.printStackTrace();
Toast.makeText(context,e.toString(),Toast.LENGTH_LONG).show();
}
}
//outside the for loop the arraylist have data( i.e fetch from Mysql database)
}
}, new Response.ErrorListener() {
@Override
public void onErrorResponse(VolleyError error) {
Toast.makeText(context,error.toString(),Toast.LENGTH_LONG).show();
}
});
Toast.makeText(context,arrayList.size()+"",Toast.LENGTH_LONG).show();
//using singleton design pattern to add the request to the queue MySingleton.getInstance(context).addToRequestQueue(jsonArrayRequest);
// here the arraylist is empty
return arrayList;
}
}
推荐答案
理解不了异步操作,你给Volley的Listener正在等待响应,并且当响应返回时,不会调用你的 return
语句服务器端,但立即被调用。这意味着你的 arrayList
只是空的(填充它的代码在响应返回后运行)。它必须是异步操作,因为如果不是用户的所有UI线程都会停止而你的应用程序不会响应任何用户操作。
It is tipical not understanding async operations, Listener which You have given to Volley is waiting for response and Your return
statement is called not when response returns from server side, but is called instantly. It means Your arrayList
is just empty ( code which fills it is running after response come back ). It must be async operations because if not all UI thread for user would just stop and Your application would not respond for any user action.
所以要解决这个问题你需要等到响应返回后再填充数组调用下一个想要的流程。好的是添加一些加载器视图,在开始请求之前显示它并在请求结束后隐藏。
So to fix this problem You need to wait until response will return and then after filling array call next wanted flow. Good is to add some loader view, show it before starting of request and hide after end of request.
可能有一些流量比较。
当前流程:
- 凌空请求开始
- 返回arrayList(空列表)
- 排球响应正在填充arrayList
通缉流程:
- show loader
- 凌空请求开始
- 凌空响应正在填充arrayList
- 隐藏加载程序
- 在准备好使用arrayList的响应后调用想要的操作
- show loader
- start of volley request
- volley response is filling arrayList
- hide loader
- call wanted action after response with ready to use arrayList
编辑(关于装载机)
对于装载可以使用任何使用 VISIBILITY 等视图属性查看(例如带图像的简单视图),因此当加载程序视图应该可见时,只需调用 loaderView.setVisibility(View.VISIBLE)
以及何时应隐藏 - loaderView.setVisibility(Vie w.GONE)
。
For loading can be used any view ( for example simple view with image ) by using view properties like VISIBILITY, so when loader view should be visible just call loaderView.setVisibility(View.VISIBLE)
and when should be hidden - loaderView.setVisibility(View.GONE)
.
为了这个目的,也可以使用一个随时可用的Android库,如 ContentLoadingProgressBar 。
To this purpose also can be used one of ready to use android libraries like ContentLoadingProgressBar.
ContentLoadingProgressBar 的示例用法。
首先将其添加到布局:
<android.support.v4.widget.ContentLoadingProgressBar
android:id="@+id/loader"
style="?android:attr/progressBarStyleLarge"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:visibility="gone" />
下一个在Activity中找到它:
Next in Activity find it by:
ContentLoadingProgressBar loader = (ContentLoadingProgressBar)findViewById(R.id.loader);
最后只是用它来显示 loader.show()
,用于隐藏 loader.hide()
。所以回到主要观点 - 在请求之前显示,隐藏在响应侦听器中。
And last just use it, for showing loader.show()
, for hidding loader.hide()
. So back to main point - show before request, hide inside in response listener.
这篇关于使用volley库,在onResponse方法中,ArrayList有一些数据,但在OnResponse方法之外,arraylist是空的的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!