React native 在RxJava订阅链中,我应该在哪里设置BackPressureBuffer(n)?

React native 在RxJava订阅链中,我应该在哪里设置BackPressureBuffer(n)?,react-native,rx-java,react-native-ble-plx,React Native,Rx Java,React Native Ble Plx,我正在尝试热修复现有的React本机库,并在中添加onBackPressureBuffer() 我知道这很难看,但我现在没有时间提交公关,有一个解决问题的方法。 我这样做是因为事件发射器的工作频率是200Hz。我需要一种安全的方法来缓冲本机端的项目,同时在JavaScript端以自己的速度使用它们 因此,代码如下所示: final Subscription subscription = Observable.defer(new Func0<Observable<Obse

我正在尝试热修复现有的React本机库,并在中添加onBackPressureBuffer()

我知道这很难看,但我现在没有时间提交公关,有一个解决问题的方法。 我这样做是因为事件发射器的工作频率是200Hz。我需要一种安全的方法来缓冲本机端的项目,同时在JavaScript端以自己的速度使用它们

因此,代码如下所示:

       final Subscription subscription = Observable.defer(new Func0<Observable<Observable<byte[]>>>() {
            @Override
            public Observable<Observable<byte[]>> call() {
                int properties = gattCharacteristic.getProperties();
                BluetoothGattDescriptor cccDescriptor = gattCharacteristic
                        .getDescriptor(Characteristic.CLIENT_CHARACTERISTIC_CONFIG_UUID);
                NotificationSetupMode setupMode = cccDescriptor != null ? NotificationSetupMode.QUICK_SETUP
                        : NotificationSetupMode.COMPAT;
                if ((properties & BluetoothGattCharacteristic.PROPERTY_NOTIFY) != 0) {
                    return connection.setupNotification(gattCharacteristic, setupMode);
                }

                if ((properties & BluetoothGattCharacteristic.PROPERTY_INDICATE) != 0) {
                    return connection.setupIndication(gattCharacteristic, setupMode);
                }

                return Observable.error(new CannotMonitorCharacteristicException(gattCharacteristic));
            }
        }).onBackpressureBuffer(1000)  <---- Here is my modification
.flatMap(new Func1<Observable<byte[]>, Observable<byte[]>>() {
            @Override
            public Observable<byte[]> call(Observable<byte[]> observable) {
                return observable;
            }
        }).doOnUnsubscribe(new Action0() {
            @Override
            public void call() {
                promise.resolve(null);
                transactions.removeSubscription(transactionId);
            }
        }).subscribe(new Observer<byte[]>() {
            @Override
            public void onCompleted() {
                promise.resolve(null);
                transactions.removeSubscription(transactionId);
            }

            @Override
            public void onError(Throwable e) {
                errorConverter.toError(e).reject(promise);
                transactions.removeSubscription(transactionId);
            }

            @Override
            public void onNext(byte[] bytes) {
                characteristic.logValue("Notification from", bytes);
                WritableArray jsResult = Arguments.createArray();
                jsResult.pushNull();
                jsResult.pushMap(characteristic.toJSObject(bytes));
                jsResult.pushString(transactionId);
                sendEvent(Event.ReadEvent, jsResult);
            }
        });
final Subscription=Observable.defer(新函数0(){
@凌驾
公共可观测呼叫(){
int properties=gattCharacteristic.getProperties();
蓝牙GattDescriptor CCCDDescriptor=gattCharacteristic
.getDescriptor(Characteristic.CLIENT\u Characteristic\u CONFIG\u UUID);
NotificationSetupMode setupMode=CCCDDescriptor!=null?NotificationSetupMode.QUICK\u设置
:NotificationSetupMode.COMPAT;
if((属性和BluetoothGattCharacteristic.PROPERTY_NOTIFY)!=0){
返回连接.setupNotification(gattCharacteristic,setupMode);
}
if((属性和BluetoothGattCharacteristic.PROPERTY_指示)!=0){
回路连接。设置指示(gattCharacteristic,设置模式);
}
返回可观察错误(新的CannotMonitorCharacteristicException(gattCharacteristic));
}

}).onBackpressureBuffer(1000)正如您所说,您正面临一个
react native
库的问题,并且上面的代码以前确实抛出了
MissingBackpressureException

.onBackpressureDrop()
的Javadoc(粗体):

指示发射项目的速度快于其观察者消耗项目的可观察者丢弃项目, 与其发射,不如发射观察者不准备观察的项目。 如果下游请求计数达到0,则可观察对象将不调用{@code onNext},直到 观察者再次调用{@code request(n)}以增加请求计数

背压: 操作员接受来自下游的背压,并以无界形式消耗源{@code Observable} 方式(即不向其施加背压)。 调度程序: 默认情况下,{@code onBackpressureDrop}不会在特定的{@link Scheduler}上运行。 您可以看到链中的下一个操作符是
.flatMap()
.dounsubscribe()
.subscribe()

.flatMap()
的Javadoc中,关于背压:

背压: 操作员接受来自下游的背压。外部{@code Observable}被消耗 在无界模式下(即,不向其施加背压)。内部{@code-Observable}应该遵守 背压;如果违反,操作员可能会发出信号{@code missingbackpressureeexception}

Javadoc
.dounsubscribe()

背压: {@code dounsubscribe}不与背压请求或价值传递交互;背压 行为在其上游和下游之间保持不变

.subscribe()

背压: 运算符以无限制的方式使用源{@code Observable}(即,no 对其施加背压)

如您所见,下面的
.onBackpressure*()
运算符都不会对其施加背压。您需要添加一个运算符,该运算符在
.onBackpressure*()
之后立即执行此操作。其中一个操作符是
.observeOn(调度器)

Javadoc
.observeOn()

背压: 此运算符接受来自下游的背压,并期望来自源{@code Observable}。违反这个 期望值将导致{@code missingbackpressureeexception}。这是异常发生时最常见的运算符 弹出窗口;寻找不支持背压的供应链上游来源, 例如{@code interval}、{@code timer}、{code PublishSubject}或{@code BehaviorSubject}并应用任何 在应用{@code-observeOn}自身之前,{@code-onbackpressurexx}操作符的

因此,一个可行的代码可以如下所示:

final Subscription subscription = Observable.defer(new Func0<Observable<Observable<byte[]>>>() {
    @Override
    public Observable<Observable<byte[]>> call() {
        int properties = gattCharacteristic.getProperties();
        BluetoothGattDescriptor cccDescriptor = gattCharacteristic
                .getDescriptor(Characteristic.CLIENT_CHARACTERISTIC_CONFIG_UUID);
        NotificationSetupMode setupMode = cccDescriptor != null ? NotificationSetupMode.QUICK_SETUP
                : NotificationSetupMode.COMPAT;
        if ((properties & BluetoothGattCharacteristic.PROPERTY_NOTIFY) != 0) {
            return connection.setupNotification(gattCharacteristic, setupMode);
        }

        if ((properties & BluetoothGattCharacteristic.PROPERTY_INDICATE) != 0) {
            return connection.setupIndication(gattCharacteristic, setupMode);
        }

        return Observable.error(new CannotMonitorCharacteristicException(gattCharacteristic));
    }
})
.flatMap(new Func1<Observable<byte[]>, Observable<byte[]>>() {
    @Override
    public Observable<byte[]> call(Observable<byte[]> observable) {
        return observable;
    }
})
.doOnUnsubscribe(new Action0() {
    @Override
    public void call() {
        promise.resolve(null);
        transactions.removeSubscription(transactionId);
    }
})
.onBackpressureBuffer(1000) // <---- Here is my modification
.observeOn(Schedulers.trampoline()) // <---- an operator that does backpressure the above
.subscribe(new Observer<byte[]>() {
    @Override
    public void onCompleted() {
        promise.resolve(null);
        transactions.removeSubscription(transactionId);
    }

    @Override
    public void onError(Throwable e) {
        errorConverter.toError(e).reject(promise);
        transactions.removeSubscription(transactionId);
    }

    @Override
    public void onNext(byte[] bytes) {
        characteristic.logValue("Notification from", bytes);
        WritableArray jsResult = Arguments.createArray();
        jsResult.pushNull();
        jsResult.pushMap(characteristic.toJSObject(bytes));
        jsResult.pushString(transactionId);
        sendEvent(Event.ReadEvent, jsResult);
    }
});
final Subscription=Observable.defer(新函数0(){
@凌驾
公共可观测呼叫(){
int properties=gattCharacteristic.getProperties();
蓝牙GattDescriptor CCCDDescriptor=gattCharacteristic
.getDescriptor(Characteristic.CLIENT\u Characteristic\u CONFIG\u UUID);
NotificationSetupMode setupMode=CCCDDescriptor!=null?NotificationSetupMode.QUICK\u设置
:NotificationSetupMode.COMPAT;
if((属性和BluetoothGattCharacteristic.PROPERTY_NOTIFY)!=0){
返回连接.setupNotification(gattCharacteristic,setupMode);
}
if((属性和BluetoothGattCharacteristic.PROPERTY_指示)!=0){
回路连接。设置指示(gattCharacteristic,设置模式);
}
返回可观察错误(新的CannotMonitorCharacteristicException(gattCharacteristic));
}
})
.flatMap(新函数1(){
@凌驾
公共可观察呼叫(可观察){
可观测收益;
}
})
.dounsubscribe(新操作0(){
@凌驾
公开作废通知(){
承诺。解决(空);
transactions.removeSubscription(transactionId);
}
})

.onBackpressureBuffer(1000)//我会试试,几个小时后再回来找你。请继续关注。这似乎正在发挥作用,等待更多的时间确认。我以前不知道RxJava的实现细节。我曾经在c#中使用被动扩展,默认情况下有缓冲。此外,在我的头脑中,onBackPressureBuffer将应用于下游,而不需要其他任何东西