当前位置: 首页 > 知识库问答 >
问题:

Firestore收集后返回值。get()已完成该操作

简嘉赐
2023-03-14

我运行的代码与这个问题中的问题类似,只是从每个文档中提取数组,并将它们的元素添加到全局数组列表中。之后,在集合之外。get(),我对该数组执行一个操作并返回。但是,如果我登录。d从onSuccess侦听器中获取全局ArrayList大小,它给出了正确的答案,但如果我在集合之外这样做。get()它总是给出0。我的问题是,我无法从onSuccess中返回,因为这不会返回我的整个函数,所以我需要在收集之后执行。get(),其中尚未填充ArrayList,可能是因为get()操作返回了一个任务

public static boolean Validator(final String sometext) {
    FirebaseFirestore db = FirebaseFirestore.getInstance();

    final ArrayList<String> mArrayList = new ArrayList<>();

    db.collection("my_collection").get()
        .addOnSuccessListener(new OnSuccessListener<QuerySnapshot>() {
            @Override
            public void onSuccess(QuerySnapshot queryDocumentSnapshots) {
                if (queryDocumentSnapshots.isEmpty()) {
                    Log.d(TAG, "Validator onSuccess: LIST EMPTY");
                    return;
                } else {

                    // Convert the Query Snapshot to a list of Document Snapshots, in this
                    // case, one document for each my_collection
                    List<DocumentSnapshot> my_collections = queryDocumentSnapshots.getDocuments();


                    for (int i = 0; i < my_collections.size(); i++) {
                        ArrayList<String> mArrayitems = (ArrayList<String>) my_collections.get(i).get("array");

                        for (int j = 0; j < mArrayitems.size(); j++) {
                            Log.d(TAG, "Adding array: " + mArrayitems.get(j).toString());
                            mArrayList.add(mArrayitems.get(j).toString());
                        }
                    }
                    Log.d(TAG, "Validator onSuccess: array list built");
                }
            }
        })
        .addOnFailureListener(new OnFailureListener() {
            @Override
            public void onFailure(@NonNull Exception e) {
                Log.d(TAG, "Validator onFailure: " + e);
            }
        });

  // check if the given sometext matches a array in the list
  Log.d(TAG, "array list size: " + mArrayList.size());
  if (mArrayList.size() > 0) {
    for (int i = 0; i < mArrayList.size(); i++) {
        if (sometext.endsWith(mArrayList.get(i))) {
            return true
        }
      }
   }
   return false;
 }

编辑:
我试图用回调来做到这一点,看起来像:

// constructor
public Validator(String sometext) {
    this.valid = false;
    this.sometext = sometext
}

public interface myCallback{
    void onCallback(boolean valid);
}

public boolean validate() {

  readData(new MyCallback() {
        @Override
        public void onCallback(boolean valid) {
            setValid(valid);
        }
    });
  return this.valid;
 }

private void readData(final MyCallback myCallback) {
    FirebaseFirestore db = FirebaseFirestore.getInstance();

    db.collection("my_collection").get()
            .addOnSuccessListener(new OnSuccessListener<QuerySnapshot>() {
                @Override
                public void onSuccess(QuerySnapshot queryDocumentSnapshots) {
                    if (queryDocumentSnapshots.isEmpty()) {
                        Log.d(TAG, "Validator onSuccess: LIST EMPTY");
                    } else {

                        List<DocumentSnapshot> my_collections = queryDocumentSnapshots.getDocuments();

                        ArrayList<String> mArrayList = new ArrayList<>();

                        for (int i = 0; i < my_collections.size(); i++) {
                            ArrayList<String> mArrayItems = (ArrayList<String>) my_collections.get(i).get("array");
                            for (int j = 0; j < mArrayItems.size(); j++) {
                                Log.d(TAG, "Adding array: " + mArrayItems.get(j).toString());
                                mArrayList.add(mArrayItems.get(j).toString());
                            }
                        }

                        boolean result = false;

                        Log.d(TAG, "array list size: " + mArrayList.size());
                        if (mArrayList.size() > 0) {
                            for (int i = 0; i < mArrayList.size(); i++) {
                                if (sometext.endsWith(mArrayList.get(i))) {
                                    result = true;
                                    Log.d(TAG, "MATCH FOUND");
                                    break;
                                }
                            }
                        }

                        myCallback.onCallback(result);

                    }
                }
            })
            .addOnFailureListener(new OnFailureListener() {
                @Override
                public void onFailure(@NonNull Exception e) {
                    Log.d(TAG, "Validator onFailure: " + e);
                }
            });
}

我遇到的问题是,在验证()中,我想在回调完成后返回正确的有效值,因为它在回调完成前返回不正确的值。


共有1个答案

焦苏燕
2023-03-14

我能够通过首先在这里使用@AlexMamo的解决方案来解决我的问题,然后在这里使用这个解决方案来监听正在更改的有效变量。

public class ValidatorVariable {
    private boolean valid;
    private ChangeListener listener;

    public boolean isValid(){
        return valid;
    }

    public void setValid(boolean valid){
        this.valid = valid;
        if (listener != null) listener.onChange();
    }

    public ChangeListener getListener(){
        return listener;
    }

    public void setListener(ChangeListener listener){
        this.listener = listener;
    }

    public interface ChangeListener {
        void onChange();
    }
}

与以下内容一起使用:

ValidatorVariable vv = new ValidatorVariable();
        vv.setListener(new ValidatorVariable.ChangeListener() {
            @Override
            public void onChange() {
                if (vv.isValid()){
                    // do stuf
                }
            }
        });
 类似资料:
  • 我使用JavaFX中的时间线对进行倒计时: 我想在时间线结束后返回一个值: 下面是一个最小的、完整的、可验证的示例: 您可以看到它首先显示“countdown Finished”并向下倒数到0,而不是从倒计时开始并向下倒数到“countdown Finished”。

  • 当集合中的文档存在或不存在时,我想返回True或False。但它总是返回错误。 我还在学习,谢谢你的帮助。

  • 我有一点奇怪的情况,似乎不允许这个挂钩适合任何广泛建立的CompletableFuture漏洞。 在评估返回布尔值的主要方法中,我希望允许对三个不同方法的调用异步完成。这三个方法中的每一个都可以返回TRUE或FALSE。 如果任何返回FALSE,我希望评估删除余数并简单地返回FALSE值。重点是,它可以是三个中的任何一个,不一定是第一个。 但最重要的是,我需要在实际返回TRUE之前等待所有三个返回

  • 我基于java的CompletableFuture构建了一个任务链,它可能非常长。我的问题是CompletableFuture中的每一个任务都是一个内部类,它包含对源CompletableFuture的引用,因此不可能对已完成的CompletableForture进行垃圾收集。有没有办法避免内存泄漏? 这是一段可用于重现此错误的代码:

  • 问题内容: 我在Utilities类中使用loadImage方法,并且在通过闭包返回图像时遇到了一些麻烦。基本上因为我的代码可能返回图像或错误,所以在调用该方法时将其分配给image属性是行不通的。 我在类的方法声明中使用的方法是否错误,还是应该以不同的方式调用该方法以预期潜在的不同结果?谢谢 问题答案: 将处理程序添加到您的 loadImage 函数中: 迅捷3 像这样调用func: 斯威夫特2