ReactiveCocoa vs RxSwift -利弊?

所以现在有了swift, ReactiveCocoa的人已经为swift重写了3.0版本

此外,还有另一个名为RxSwift的项目。

我想知道人们是否可以补充关于这两个框架在设计/api/理念上的差异的信息(请本着SO的精神,坚持正确的事情,而不是关于哪个是“最好的”的意见)

[StackOverflow mods注意:这个问题确实有明确的答案,答案是两个框架之间的差异。我认为这也非常符合SO的主题。

首先,阅读他们的ReadMe后,我的第一印象是:

  • 作为一个熟悉微软的“真正的”c# Rx的人,RxSwift看起来更容易辨认。
  • ReactiveCococa现在似乎已经进入了自己的空间,引入了新的抽象概念,如Signals vs SignalProducers和Lifting。一方面,这似乎澄清了一些情况(什么是热与冷信号),但另一方面,这似乎增加了框架的复杂性很多
30538 次浏览

这是一个非常好的问题。比较这两个世界是非常困难的。Rx是其他语言(如c#、Java或JS)中的响应式扩展的一个端口。

反应可可的灵感来自函数式响应式编程,但在过去的几个月里,也被指向受响应式扩展启发。其结果是一个与Rx共享一些东西的框架,但其名称起源于FRP。

首先要说明的是,根据概念的Conal的定义, RAC和RxSwift都不是函数式响应式编程实现。从这一点开始,一切都可以简化为每个框架如何处理副作用和其他一些组件。

让我们谈谈社区和meta-tech之类的东西:

  • RAC是一个有3年历史的项目,诞生于Objective-C,后来在完全放弃Objective-C上正在进行的工作后,在3.0版本中移植到Swift(带桥接)。
  • RxSwift是一个几个月前的项目,现在似乎在社区中有一个势头。对RxSwift来说很重要的一件事是,它是在ReactiveX组织下,所有其他实现都以相同的方式工作,学习如何处理RxSwift将使Rx工作。Net, RxJava或RxJS是一个简单的任务,只是语言语法的问题。我可以说这是基于哲学一次学,处处用

现在是科技的时候了。

生产/观察实体

RAC 3.0有两个主要实体,SignalSignalProducer,第一个实体发布事件,不管是否附加订阅者,第二个实体需要start来实际产生信号/事件。这种设计是为了区分冷热观测的乏味概念,这是许多开发人员困惑的根源。这就是为什么差异可以缩小到如何处理副作用

在RxSwift中,SignalSignalProducer转换为Observable,这听起来可能令人困惑,但这两个实体在Rx世界中实际上是相同的东西。在RxSwift中创建__abc2的设计必须考虑它们是热的还是冷的,这听起来可能是不必要的复杂性,但一旦你理解了它们的工作原理(再次热/冷/暖只是订阅/观察时的副作用),它们就可以被驯服。

在这两个世界中,订阅的概念基本上是相同的,有一点不同是RAC引入的,即在发送完成事件之前释放Signal时的interruption事件。 概括一下,两者都有以下类型的事件:

  • Next,来计算新的接收值
  • Error,来计算一个错误并完成流,取消订阅所有的观察者
  • Complete,将流标记为已完成取消订阅所有观察者

此外,RAC还有interrupted,当Signal在正确完成或错误完成之前被释放时,会发送该interrupted

手动编写

在RAC中,Signal/SignalProducer是只读实体,它们不能从外部管理,RxSwift中的Observable也是如此。要将Signal/SignalProducer转换为可写实体,必须使用pipe()函数返回一个手动控制的项。在Rx空间中,这是一个不同的类型,称为Subject

如果读/写的概念听起来不熟悉,可以用Future/Promise做一个很好的类比。Future是一个只读占位符,就像Signal/SignalProducerObservable,另一方面,Promise可以手动实现,就像pipe()Subject

调度器

这个实体在两个世界中是非常相似的,相同的概念,但RAC是串行的,而RxSwift还具有并发调度器。

作文

组合是响应式编程的关键特征。构成流是这两个框架的本质,在RxSwift中它们也被称为序列

RxSwift中的所有可观察实体都是ObservableType类型,所以我们用相同的操作符组合SubjectObservable的实例,而不需要考虑任何额外的问题。

在RAC空间中,SignalSignalProducer是两个不同的实体,我们必须在SignalProducerlift才能将生成的东西与Signal的实例组合在一起。这两个实体都有自己的操作符,所以当你需要混合东西时,你必须确保某个操作符是可用的,另一方面,你忘记了热/冷的可观察值。

关于这一部分,科林爱伯哈总结得很好:

看看当前的API,信号操作主要集中在“下一个”事件上,允许你在不同的线程上转换值、跳过、延迟、组合和观察。而信号产生器API主要关注信号生命周期事件(completed, error),操作包括then, flatMap, takeUntil和catch。

额外的

RAC还有ActionProperty的概念,前者是计算副作用的类型,主要与用户交互有关,后者是在观察值发生变化时执行任务的有趣类型。在RxSwift中,Action再次转换为Observable,这在RxCocoa中很好地显示出来,这是iOS和Mac的Rx原语的集成。在RxSwift中,RAC的Property可以转换为Variable(或BehaviourSubject)。

重要的是要理解Property/Variable是我们必须将命令式世界与响应式编程的声明性本质连接起来的方式,因此在处理第三方库或iOS/Mac空间的核心功能时,有时它是一个基本组件。

结论

RAC和RxSwift是两种完全不同的野兽,前者在Cocoa领域有很长的历史,有很多贡献者,后者相当年轻,但依赖于在其他语言(如Java、JS或。net)中被证明有效的概念。哪个更好的决定取决于个人偏好。RAC表示,热/冷可观测的分离是必要的,这是框架的核心特性,RxSwift表示,它们的统一比分离更好,再次强调,这只是关于如何管理/执行副作用。

RAC 3.0似乎在分离热/冷可观察对象的主要目标之上引入了一些意想不到的复杂性,如中断的概念,在两个实体之间分割操作符,并引入一些必要的行为,如start,以开始产生信号。对某些人来说,这些东西可能是一件好事,甚至是一个杀手功能,对另一些人来说,它们可能只是不必要的,甚至是危险的。另一件需要记住的事情是,RAC试图尽可能地跟上Cocoa的惯例,所以如果你是一个有经验的Cocoa Dev,你应该会觉得使用它比使用RxSwift更舒服。

另一方面,RxSwift存在所有的缺点,比如热/冷的可观察对象,但也有响应式扩展的优点。从RxJS, RxJava或Rx。Net到RxSwift是一件简单的事情,所有的概念都是一样的,所以这使得寻找材料非常有趣,也许你现在面临的同样的问题,已经被RxJava中的某人解决了,解决方案可以重新应用,考虑到平台。

选哪一个肯定是个人喜好的问题,从客观的角度不可能说哪一个更好。唯一的办法就是放弃Xcode,同时尝试这两个软件,然后选择一个使用起来更舒服的。它们是类似概念的两个实现,试图实现相同的目标:简化软件开发。