Evaluation of as.integer(max(factorize(15)))
This appears quite bizarre to me and I would like 开发者_开发问答an explanation. I
library(gmp)
factorize(15) # => "3" "5"
max(factorize(15)) # => "5"
as.integer("5") # => 5
as.integer(max(factorize(15))) # => 1 0 0 0 1 0 0 0 1 0 0 0 5 0 0 0
I can do what I want with:
max(as.numeric(factorize(15))) # => [1]5
But it shook me that I couldn't rely on nesting functions inside of functions in a supposedly scheme-like language. Am I missing anything?
Well, the answer is in the representation of factorize(15)
:
> dput(factorize(15))
structure(c(02, 00, 00, 00, 01, 00, 00, 00, 01, 00, 00, 00, 03,
00, 00, 00, 01, 00, 00, 00, 01, 00, 00, 00, 05, 00, 00, 00), class = "bigz")
and
> dput(max(factorize(15)))
structure(c(01, 00, 00, 00, 01, 00, 00, 00, 01, 00, 00, 00, 05,
00, 00, 00), class = "bigz")
...max
and as.numeric
(actually, as.double
) have methods for the bigz
class, but apparently as.integer
does not:
> methods(max)
[1] max.bigq max.bigz
> methods(as.numeric)
no methods were found
> methods(as.double)
[1] as.double.bigq as.double.bigz as.double.difftime as.double.POSIXlt
> methods(as.integer)
no methods were found
...so as.integer
treats the bigz
objects as a simple vector of values.
The result of factorize
in package gmp
is a object of class bigz
:
> factorize(15)
[1] "3" "5"
> str(factorize(15))
Class 'bigz' raw [1:28] 02 00 00 00 ...
From the help for ?biginteger
it seems the following coercion functions are defined for objects of class bigz
:
as.character
as.double
Notice there is no as.integer
in the list. So, to convert your result to numeric, you must use as.double
:
> as.double(max(factorize(15)))
[1] 5
I agree that it seems odd that the 'bigz' class does not have an as.integer method. However, it may be that the whole point of the gmp package is to keep its values "out of the hands" of the less capable regular R representation structures. The authors did not choose (yet) to offer an integer coercion function but you could always suggest to them that they should. As @Andrie demonstrated, such a function can be defined to intercept what would otherwise would be a .Primitive call, which is what you now get with as.integer()
.
require(gmp)
methods(as)
精彩评论