Note that there are some explanatory texts on larger screens.

plurals
  1. POConverting package using S3 to S4 classes, is there going to be performance drop?
    text
    copied!<p>I have an R package which currently uses <code>S3</code> class system, with two different classes and several methods for generic S3 functions like <code>plot</code>, <code>logLik</code> and <code>update</code> (for model formula updating). As my code has become more complex with all the validity checking and <code>if/else</code> structures due to to the fact that there's no inheritance or dispatching based on two arguments in <code>S3</code>, I have started to think of converting my package to <code>S4</code>. But then I started to read about the advantages and and disadvantages of <code>S3</code> versus <code>S4</code>, and I'm not so sure anymore. I found <a href="http://www.r-bloggers.com/s3-vs-s4-efficiency-issues/" rel="nofollow noreferrer">R-bloggers blog post</a> about efficiency issues in S3 vs S4, and as that was 5 years ago, I tested the same thing now:</p> <pre><code>library(microbenchmark) setClass("MyClass", representation(x="numeric")) microbenchmark(structure(list(x=rep(1, 10^7)), class="MyS3Class"), new("MyClass", x=rep(1, 10^7)) ) Unit: milliseconds expr structure(list(x = rep(1, 10^7)), class = "MyS3Class") new("MyClass", x = rep(1, 10^7)) min lq median uq max neval 148.75049 152.3811 155.2263 159.8090 323.5678 100 75.15198 123.4804 129.6588 131.5031 241.8913 100 </code></pre> <p>So in this simple example, <code>S4</code> was actually bit faster. Then I read <a href="https://stackoverflow.com/questions/3602154/when-does-it-pay-off-to-use-s4-methods-in-r-programming">SO question</a> about using <code>S3</code> vs <code>S4</code>, which was quite much in favor of <code>S3</code>. Especially @joshua-ulrich 's answer made me doubt against <code>S4</code>, as it said that </p> <blockquote> <p>any slot change requires a full object copy</p> </blockquote> <p>That feels like a big issue if I consider my case where I'm updating my object in every iteration when optimizing log-likelihood of my model. After some googling I found <a href="http://r.789695.n4.nabble.com/Small-changes-to-big-objects-1-td4654566.html" rel="nofollow noreferrer">John Chambers post</a> about this issue, which seems to be changing in R 3.0.0.</p> <p>So although I feel it would be beneficial to use <code>S4</code> classes for some clarity in my codes (for example more classes inheriting from the main model class), and for the validity checks etc, I am now wondering is it worth all the work in terms of performance? So, performance wise, is there real performance differences between <code>S3</code> and <code>S4</code>? Is there some other performance issues I should be considering? Or is it even possible to say something about this issue in general?</p> <p>EDIT: As @DWin and @g-grothendieck suggested, the above benchmarking doesn't consider the case where the slot of an existing object is altered. So here's another benchmark which is more relevant to the true application (the functions in the example could be get/set functions for some elements in the model, which are altered when maximizing the log-likelihood):</p> <pre><code>objS3&lt;-structure(list(x=rep(1, 10^3), z=matrix(0,10,10), y=matrix(0,10,10)), class="MyS3Class") fnS3&lt;-function(obj,a){ obj$y&lt;-a obj } setClass("MyClass", representation(x="numeric",z="matrix",y="matrix")) objS4&lt;-new("MyClass", x=rep(1, 10^3),z=matrix(0,10,10),y=matrix(0,10,10)) fnS4&lt;-function(obj,a){ obj@y&lt;-a obj } a&lt;-matrix(1:100,10,10) microbenchmark(fnS3(objS3,a),fnS4(objS4,a)) Unit: microseconds expr min lq median uq max neval fnS3(objS3, a) 6.531 7.464 7.932 9.331 26.591 100 fnS4(objS4, a) 21.459 22.393 23.325 23.792 73.708 100 </code></pre> <p>The benchmarks are performed on R 2.15.2, on 64bit Windows 7. So here <code>S4</code> is clearly slower.</p>
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload