在 R 编程中使用 S4 方法啥时候有回报
Posted
技术标签:
【中文标题】在 R 编程中使用 S4 方法啥时候有回报【英文标题】:When does it pay off to use S4 methods in R programming在 R 编程中使用 S4 方法什么时候有回报 【发布时间】:2011-04-05 20:29:53 【问题描述】:我经常在专业环境中使用 R 进行编程,我也为客户或同事编写包。这里的一些程序员有 Java 背景,坚持以面向对象的方式做所有事情,使用 S4 方法。另一方面,我的经验是,当试图让代码做你想做的事情时,S4 实现的性能通常会更差,并且会引起更多的头痛。
我绝对同意,在某些情况下,您必须能够以受控方式构造复杂对象或附加现有对象。但大多数时候,S4 实现也可以使用经典列表轻松完成,而无需像定义标准泛型、方法、构造函数、初始化程序等那样麻烦。
您何时考虑为 R 编写 S4 实现?
编辑:为了清楚起见,我非常感谢 R 中关于 OO 的一般答案和讨论。OOP 可以在 R 中以多种方式完成,但我的问题实际上是针对专门使用 S4 方法的附加值。
【问题讨论】:
但是 S3 是一个合法的面向对象!它比 S4 更现代、更灵活。 @Joris 多重继承?可以通过将对象及其类与c
合并来完成。正式验证?没有人说 OOP 必须通过严格的类型来完成; Smalltalk 就是一个引人注目的例子。总的来说,我认为 OOP 只是一种方式,因此没有“规范”的 OOP(尽管人们通常会选择他们最喜欢的语言并说它定义了它)。
@mbq :好的,那么你就明白什么是 OOP 什么不是了。您可以通过仅使用列表并手动设置所有属性来轻松地编程面向对象的方式。 My Colleagues 来自 Java 背景,如果它迫使您以面向对象的方式进行操作,则称为 OOP。 S3 没有,S4 为他们做,我也有同样的感觉。您的里程可能会有所不同,但我认为您确实同意 S3 和 S4 是两种不同的野兽。我想要一些关于 S4 使用的想法,而不是关于 R 中的 OOP 到底是什么的语义讨论。
我认为部分问题在于 S3 和 S4 都没有提供真正符合 Java/C++ 类型世界的人将习惯的 OO 结构,一切都在进行对于精通这种 OO 风格的人与接触过 Lisp、Dylan 等的人来说,显得陌生。
@geoffjentry 好点!而这并不会使它们“少 OO”。
【参考方案1】:
我的经验和你一致,所以我只使用 S3。
澄清一下:S4 有一些巧妙的功能(例如,在多个参数上调度和插槽类型检查),但我还没有遇到过功能超过成本的情况。成本示例包括:任何槽更改都需要完整的对象副本以及(可能更糟)对 S4 方法的持续更改。
简而言之,我喜欢 S4 背后的想法,但我会等待它成熟后再在我自己的代码中使用它。
【讨论】:
那么,五年后……你还继续坚持使用 S3 吗? @isomorphismes:是的。不过,我对 R6 作为 S4 的替代品很感兴趣。 @JoshuaUlrich:您是说 R6 是 S4 的替代品,还是说它有不同的用例?【参考方案2】:我假设这并不直接适用于您,但如果您正在为 Bioconductor 开发软件包,那么就有使用 S4 的动机,因为他们积极鼓励使用 S4,并且在过去十年的大部分时间里都有使用 - 所以所有的核心包大量使用 S4。
我发现所有额外的开销都是一种痛苦——setGeneric、setMethod、处理 NAMESPACE 等等。话虽如此,我发现它强加的结构、可扩展性的潜力和其他类似的事情都是值得的.与所有事情一样,都需要权衡取舍。我认为它可以更干净 - 我不喜欢 S3 方法如何通过命名约定(foo.class)简单地伪装。尽管如此,我倾向于避免在自己的代码中大量使用 S4,除非有人告诉我这样做。
【讨论】:
【参考方案3】:好问题!我希望它能引起一些深思熟虑的讨论......
我从未使用过,也不打算使用它,原因如下:
-
性能
我没有耐心完全理解 S4 以及它与 S3 的关系。
语法糖:我宁愿拥有 object.method() 而不是 method(object)。
我喜欢suguar,我能说什么呢!
【讨论】:
我也不用S4,因为我喜欢object.method()
。谷歌的 R 风格说:“使用 S3 对象和方法,除非有充分的理由使用 S4 对象或方法。S4 对象的主要理由是直接在 C++ 代码中使用对象。S4 泛型的主要理由/方法是发送两个参数”
FWIW,为什么 Google 是 R 风格的权威? R-core在这件事上不应该是更高的权威吗? (并不是说 R-core 在他们对此事的看法上似乎是统一的,而是……)。正是因为这个原因,Google R 风格指南的***让我有点恼火。
@geoffjentry 我的一部分感觉就是这种说法……但是,我很高兴人们只是稍微考虑一下风格。如果在 PDF 上有 GOOG 徽标让一些经济学家(或统计学家等)阅读它,那么我完全赞成。我厌倦了尝试阅读由于格式和样式而难以解析的代码。
当然,如果他们愿意,R-core 可以轻松解决这个问题,所以我想他们要么对 Google 指南感到满意,要么根本不关心 Google 指南。编辑:从这个帖子(tinyurl.com/3ydaa89)来看,达尔加德和默多克都回答了我猜这更多的是冷漠的角度。【参考方案4】:
我学习 S4 是为了扩展动物轨迹数据的空间 (sp) 类。这是可用选项中的最佳选择(最一致、通用且与许多 GIS 定义最匹配),以避免从头开始编写所需的所有内容。我并不觉得 S4 像很多人说的那样繁重,但我现在已经习惯于探索像这样的对象的底层结构。性能也不错,我觉得可以做的很好,但是做的不好会有性能的陷阱。
如果您对空间数据感兴趣,spatstat 是一个很好的例子,说明如何在 S3 中执行许多与 sp 类似的事情,但是(就像看似所有空间数据一样......)数据结构之间几乎没有明确的类比在不同的软件中。
【讨论】:
【参考方案5】:S4 类在空间统计(sensu 包sp
)中发挥着重要作用,从一种数据类型到另一种数据类型的转换似乎是无缝的。这样做的缺陷是调试,根据我的经验,调试充其量是乏味的。
到目前为止,我已经使用 S3 进行了管理,但将来可能会考虑使用 S4。
随着时间的推移,随着事情的发展,我相信它们至少会在 R 的各个领域(可能是空间分析、计量经济学、环境计量学......)的核心特征中发挥重要作用
【讨论】:
事实上,越来越多的 R 部分在 S4 类中重新编码,但在使用这些包时我遇到了越来越多的问题。文档是针对立即使用的,但缺乏在编程中的使用。如您所知,我在使用许多包的 S4 编码方法评估函数参数时也遇到了麻烦。所以我倾向于远离它们,我希望有人能给我一个很好的用途。【参考方案6】:别忘了还有 R.oo(在 CRAN 上),它提供了在 R 中执行 OO 的第三种方式。在我看来,这提供了一个 OO 系统,对于从其他系统迁移的程序员来说可能更熟悉 - 特别是拥有泛型函数(因此 print(foo) 然后必须在 foo 的类上调度)方法与对象相关联,所以你会做 foo$print() - 就像在 python 或 C++ 中你会做foo.print().
【讨论】:
我以前见过这个,但我一直想知道额外的附加值是什么。除了语义,我找不到与 S3 编程的任何区别。但老实说,我并没有深入研究它。【参考方案7】:曾几何时,Roxygen2 不喜欢 S4 方法。截至 2017 年(至少),他们一起工作。
我不幸创建了一些需要方法来处理 S3 和 S4 类的函数。由于 R-core 多次更改了有关这些系统如何交互、命名空间如何工作以及 Rcmd 检查如何工作的细节,因此多年来保持这段代码工作非常痛苦。
如果您不喜欢 Google 的样式指南,请考虑来自 R-help 上的这些知名 R 包开发人员的 cmets
弗兰克·哈雷尔 “如果您热爱计算机科学胜过珍惜自己的时间,请使用 S4。”
Terry Therneau 写道: 对于我所做的 90% 的工作,我强烈喜欢松散的 (S3) 而不是刚性的 (S4) 类……我对 S4 与 S3 的总结
S4 在以下方面有很大的增量: 1.讨厌写 2.调试困难 3. 编写非常晦涩的代码的能力 4. 设计
S4 收获: 5. 指导自动转换的能力 6. 验证类对象的内容
【讨论】:
很久以前的更新:现在可以了以上是关于在 R 编程中使用 S4 方法啥时候有回报的主要内容,如果未能解决你的问题,请参考以下文章
在用R语言编程中,界面上出现了“+”号,是啥意思?如何删除错误的输入,如何清屏?谢谢
儿童使用Scratch编程时,与程序员在工作中的编程有啥区别
数控铣床的编程中,R代表啥含义当R所赋予的数值为负值时,代表啥含义?