[Rd] class(<matrix>) |--> c("matrix", "arrary") [was "head.matrix ..."]

Duncan Murdoch murdoch@dunc@n @end|ng |rom gm@||@com
Sun Nov 10 17:48:26 CET 2019


On 10/11/2019 9:17 a.m., Bryan Hanson wrote:
> 
> 
>> On Nov 10, 2019, at 3:36 AM, Martin Maechler <maechler using stat.math.ethz.ch> wrote:
>>
>>>>>>> Gabriel Becker
>>>>>>>     on Sat, 2 Nov 2019 12:37:08 -0700 writes:
>>
>>> I agree that we can be careful and narrow and still see a
>>> nice improvement in behavior. While Herve's point is valid
>>> and I understand his frustration, I think staying within
>>> the matrix vs c(matrix, array) space is the right scope
>>> for this work in terms of fiddling with inheritance.
>>
>> [.................]
>>
>>
>>>> Also, we seem to have a rule that inherits(x, c)  iff  c %in% class(x),
>>>
>>> good point, and that's why my usage of  inherits(.,.) was not
>>> quite to the point.  [OTOH, it was to the point, as indeed from
>>>       the ?class / ?inherits docu, S3 method dispatch and inherits
>>>       must be consistent ]
>>>
>>>> which would break -- unless we change class(x) to return the whole
>>> set of inherited classes, which I sense that we'd rather not do....
>>
>>   [................]
>>
>>> Note again that both "matrix" and "array" are special [see ?class] as
>>> being of  __implicit class__  and I am considering that this
>>> implicit class behavior for these two should be slightly
>>> changed ....
>>>
>>> And indeed I think you are right on spot and this would mean
>>> that indeed the implicit class
>>> "matrix" should rather become c("matrix", "array").
>>
>> I've made up my mind (and not been contradicted by my fellow R
>> corers) to try go there for  R 4.0.0   next April.
>>
>> I've found the few places in base R that needed a change (to
>> pass 'make check-all' in the R sources) and found that indeed a
>> overzealous check in 'Matrix' needed also a change (a place
>> where the checking code assume  class(<matrix>) |--> "matrix" ).
>>
>> There are certainly many more package (codes and checks) that
>> need adaption .. i.e., should be changed rather *before* the
>> above change is activated in R-devel (and then will affect all CRAN
>> and Bioconductor checks.)
>>
>> To this end, I've published an  'R Blog' yesterday,
>>
>>    http://bit.ly/R_blog_class_think_2x
>>
>> which translates to
>>
>>    https://developer.r-project.org/Blog/public/2019/11/09/when-you-think-class.-think-again/index.html
>>
>> notably mentioning why using  class(x) == "...."  (or '!=')  or
>> switch(class(.) ...)  is quite unsafe and hence bad and you
>> should very often not replace  class(x)  by  class(x)[1]  but
>> really use the "only truly correct" ;-)
>>
>>      inherits(x,  "...")
>> or
>>      is(x,  "....")   # if you're advanced/brave enough (:-) to
>>      	    	      # use formal classes (S4)
> 
> Thanks for the helpful blog post Martin. Is the following
> 
>    “test_class”  %in% class(some_object)
> 
> which I think in your symbols would be
> 
>    “…” %in% class(x)
> 
> safe as far as you see it? By safe, I mean equivalent to your suggestion of inherits(x, “…”) .

Those aren't equivalent if S4 gets involved.  You can see it if you run 
this code:

example("new") # Creates an object named t2 of class "trackcurve"
                # that contains "track"
inherits(t2, "track")  # TRUE
"track" %in% class(t2) # FALSE

I can't think of any examples not involving S4.

Duncan Murdoch



More information about the R-devel mailing list