【问题标题】:Is it a good practice to have big number of childEventListeners? [duplicate]拥有大量 childEventListener 是一种好习惯吗? [复制]
【发布时间】:2018-03-01 11:42:53
【问题描述】:

我用 firebase 编写了一个应用程序,用户可以在其中通过 GeoFire 在其周围显示事件。 Geofire 返回我的 eventID 列表,然后我下载这些事件。问题是,我需要监听这些事件的变化。为每个事件注册 childEventListener 是一个好习惯吗(可能有很多,比如说 100 个)?或者我有更好的方法吗?

感谢您的帮助,Honza

编辑:

赛事是具有以下字段的运动赛事:标题、描述、时间、地点、签名用户等。在我下载了我周围的事件后,我需要监听变化,这样我就可以显示谁将参加这个事件(例如足球比赛)等等。

起初我在 geofire 的帮助下下载了我周围区域的 eventID

    private  ObservableOnSubscribe<String> suggestedEventIDSource(@NonNull LatLng userLocation, int wantedNumberOfEvents, List<String> sports){
    return (e->{
        ArrayList<String> suggestedEventIDs = new ArrayList<>();


        final GeoQuery geoQuery = geoFire.queryAtLocation(new GeoLocation(userLocation.latitude,userLocation.longitude),radius);

        GeoQueryEventListener geoQueryEventListener = new GeoQueryEventListener(){

            @Override
            public void onKeyEntered(String key, GeoLocation location) {
                String[] idParts = key.split(" ");
                if((sports.size() == 0 || sports.contains(idParts[0]))
                        && !(idParts[idParts.length-1]).equals(currentUser.getUid())
                        && !(Meet2SportApp.getSignedEventIDV2().contains(key))){
                    suggestedEventIDs.add(key);
                }
            }

            @Override
            public void onKeyExited(String key) {

            }

            @Override
            public void onKeyMoved(String key, GeoLocation location) {

            }

            @Override
            public void onGeoQueryReady() {
                Log.i(TAG, "onGeoQueryReady: radius - " + radius + " events in radius - " + suggestedEventIDs.size());

                if(suggestedEventIDs.size()<wantedNumberOfEvents && radius < 50f){
                    radius++;
                    e.onComplete();
                }
                else {
                    for(String eventID : suggestedEventIDs)
                         e.onNext(eventID);
                }
            }

            @Override
            public void onGeoQueryError(DatabaseError error) {

            }
        };


        geoQuery.addGeoQueryEventListener(geoQueryEventListener);
        e.setCancellable(geoQuery::removeAllListeners);
    });
}

然后我使用 valueEventListener 下载每个事件

 private SingleOnSubscribe<DataSnapshot> sourceOfEvent(String eventID){
    return (e -> {
        RxJavaPlugins.setErrorHandler(Functions.emptyConsumer());
        Log.i(TAG, "Downloading event: " + eventID + " on thread " + Thread.currentThread().getName());
        ValueEventListener valueEventListener = new ValueEventListener() {
            @Override
            public void onDataChange(DataSnapshot dataSnapshot) {
                e.onSuccess(dataSnapshot);
            }

            @Override
            public void onCancelled(FirebaseError firebaseError) {
            }
        };
        eventDB.child(eventID).addListenerForSingleValueEvent(valueEventListener);
    });
}

这很好,但是当发生一些更改时,应用程序不会更新。 因此,如果我使用 childEventListener 而不是 valueEventListener,我会在发生某些更改时收到通知,但我可能会有大量活动的 childEventListener。

那么这是一个好的做法,还是有更好的方法?

【问题讨论】:

  • 究竟如何在事件发生后改变
  • 我假设事件是在 eventID 上触发的。所以他想捕获所有 eventID 上的所有事件?我假设一个childEventListener 只需检查哪个 eventID 触发了该事件就足够了。如果您可以改写您的问题,那就太好了,因为目前还不清楚您在问什么。请提供Minimal, Complete and Verifiyable example
  • 赛事是体育赛事,例如有赛事“足球比赛”,创建的用户可以编辑时间或地点。当其他用户登录此事件时,它会更改 numberOfSignedUsers 字段等...
  • 有了这个解释,您应该真正扩展您的原始问题,解释您使用的词语,向我们展示您正在使用的代码并向我们展示您的问题所在。
  • @Ben 问题已更新,希望更清楚:)

标签: java android firebase firebase-realtime-database geofire


【解决方案1】:

是的,您可以拥有多个 ChildEventListener,这是一个好习惯吗?您应该真正使用一个并具有 LinkedHashMap 类型的结构,以便您可以将数据分配给某个 Key,然后您可以稍后再调用它。

【讨论】:

  • 请您给我一个例子好吗?我不确定,你是怎么解决的。我可以有一个 Firebase 对节点的引用的列表或地图,我想观察(到体育赛事),但我不确定,如何将单个 childeventlistener 添加到 firebase 中的多个节点。如果能以某种方式完成,那就完美了……
  • 您能否更清楚地解释一下这个 firbase 进程是如何工作的,它是如何一个接一个地抓取每个体育赛事的,或者是一个个地抓取。如果是一个一个,你可以创建一个循环来获取数据的所有值,然后将它推到一个linkedhasmap中。
  • 首先通过geofire,应用程序下载事件的所有ID,例如1公里区域。然后为每个运动事件注册singleValueEventListener(通过eventID找到引用),然后我下载这些运动事件。如果我注册 childEventListener 而不是 singleValueEventListener,每当 firebase 中的运动事件发生变化时,应用程序都会收到通知并下载更新的运动事件。但是我会在给定区域拥有与 SportEvents 一样多的注册 childEventListeners...
  • 您应该将每个事件的所有 ID 分配给一个 Listener,然后对您获得的数据进行排序。
猜你喜欢
  • 1970-01-01
  • 2014-07-01
  • 2015-01-08
  • 2016-12-22
  • 2015-05-08
  • 2011-02-28
  • 2020-07-14
  • 2011-01-29
  • 2020-09-16
相关资源
最近更新 更多