export function getHotOffers() {
let offers;
getRequest('/hot-offers').then(x => offers = x);
alert(offers);
return JSON.parse(offers);
}
这是我输出的功能。它以异步方式向服务器发出请求并获取JSON字符串。当我调试项目时,一切正常,警报返回字符串但是当我执行代码时,警报返回undefined。我该如何解决这个问题?
答案 0 :(得分:2)
这不是承诺的工作方式。 getRequest()之后的代码并没有等待承诺完成 - 它只是立即运行。
export function getHotOffers() {
let offers;
getRequest('/hot-offers').then( x =>
//this only happens after the request is done
offers = x
);
//this code runs right away, before the request completes
alert(offers);
//so does this, so "offers" will be undefined at this point
return JSON.parse(offers);
}
请求返回后运行的所有代码都应该在你的回调中,如下所示:
export function getHotOffers() {
return getRequest('/hot-offers');
}
//somewhere else
getHotOffers().then( offers => {
useTheOffers( offers );
});
答案 1 :(得分:1)
数据不是同步可用的。您需要使用承诺才能访问优惠。
>>> b=[1, 2, 1, 1, 3, 2, 1]
>>> [sum(f(b,5,int(listt[u]),int(listt[u+1]))) for u in range(0,len(listt)-1)]
[4, 1, 5]
>>>
同样,任何调用此函数的代码都将获得一个承诺,并且必须使用其public class FragmentHome extends Fragment {
private SearchView search;
View view;
DatabaseReference dataRef;
private FirebaseListAdapter<String> firebaseListAdapter;
ListView mListView;
private TextView text;
ArrayList<String> city=new ArrayList<String>();
private int i=0;
private String data,val,var;
ArrayAdapter<String> adapter;
@Nullable
@Override
public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable final Bundle savedInstanceState) {
View v= inflater.inflate(R.layout.activity_fragment_home,container,false);
if (container!=null){
container.removeAllViews();
}
search= (SearchView) v.findViewById(R.id.search);
search.onActionViewExpanded();
search.setIconified(false);
search.setQueryHint("Search Docter By City Or Department");
mListView= (ListView) v.findViewById(R.id.mList);
mListView.setVisibility(View.INVISIBLE);
dataRef=FirebaseDatabase.getInstance().getReference().child("Docters");
adapter=new ArrayAdapter<String>(getActivity(), android.R.layout.simple_list_item_1, city);
mListView.setAdapter(adapter);
dataRef.addChildEventListener(new ChildEventListener() {
@Override
public void onChildAdded(DataSnapshot dataSnapshot, String s) {
data=dataSnapshot.child("city").getValue(String.class);
val=dataSnapshot.child("department").getValue(String.class);
if (!city.contains(data)){
city.add(data);
}
if (!city.contains(val)){
city.add(val);
}
adapter.notifyDataSetChanged();
}
@Override
public void onChildChanged(DataSnapshot dataSnapshot, String s) {
data=dataSnapshot.child("city").getValue(String.class);
val=dataSnapshot.child("department").getValue(String.class);
city.add(data);
city.add(val);
city.add(var);
adapter.notifyDataSetChanged();
}
@Override
public void onChildRemoved(DataSnapshot dataSnapshot) {
}
@Override
public void onChildMoved(DataSnapshot dataSnapshot, String s) {
}
@Override
public void onCancelled(DatabaseError databaseError) {
}
});
search.setOnQueryTextListener(new SearchView.OnQueryTextListener() {
@Override
public boolean onQueryTextSubmit(String text) {
return false;
}
@Override
public boolean onQueryTextChange(String text) {
if (!text.isEmpty()){
mListView.setVisibility(View.VISIBLE);
adapter.getFilter().filter(text);
}else{
mListView.setVisibility(View.INVISIBLE);
}
return false;
}
});
mListView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
@Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
String itemRef = (String) adapter.getItem(position);
search.setVisibility(View.INVISIBLE);
mListView.setVisibility(View.INVISIBLE);
FragmentTransaction ft=getChildFragmentManager().beginTransaction();
DocterList fragment=new DocterList();
Bundle item=new Bundle();
item.putString("item",itemRef);
fragment.setArguments(item);
ft.replace(R.id.activity_fragment_home,fragment);
ft.addToBackStack(null);
ft.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_FADE);
ft.commit();
}
});
return v;
}}
方法来获取最终值。
export function getHotOffers() {
let offerPromise = getRequest('/hot-offers')
.then(offers => JSON.parse(offers));
return offerPromise;
}
答案 2 :(得分:1)
您的代码在调用传递给then
的回调之前继续。
使用async/await
,您可以绕过这一点,并提高代码的易读性:
// emulate your "getRequest" function which returns a promise:
async function getRequest(path) {
await new Promise(resolve => setTimeout(resolve, 500)); // simulate response delay
const offers = ['hot-offer-1', 'hot-offer-2', 'hot-offer-3'];
return offers;
}
async function getHotOffers() {
const offers = await getRequest('/hot-offers');
console.log(offers);
return JSON.parse(offers);
}
getHotOffers();
&#13;