Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
401 views
in Technique[技术] by (71.8m points)

r - The representation of an empty argument in a "call"

What kind of animal is an empty argument? Consider the following piece of code.

> f <- function(...) match.call()
> l <- as.list(f(,3))
> l
[[1]]
f

[[2]]


[[3]]
[1] 3

> typeof(l[[2]])
[1] "symbol"

> identical(l[[2]],``)
Error: attempt to use zero-length variable name

> as.character(l[[2]])
[1] ""

What sorcery is that?

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

If looks like l[[2]]'s value is a special object: the empty symbol. Some facts about the empty symbol (speculated based on casual experimentation).

(1) The empty symbol is a symbol:

> is.symbol(l[[2]])
[1] TRUE

(2) The empty symbol cannot be created explicitly:

> as.name("")
Error in as.name("") : attempt to use zero-length variable name
> ``
Error: attempt to use zero-length variable name
> quote()
Error in quote() : 0 arguments passed to 'quote' which requires 1

(3) The only way to create an empty symbol is by quote-ing a function call and passing an empty argument, e.g.:

> c <- quote(f(,0))
> d <- quote(f(x, n=, 0))

The empty symbol can now be accessed thus: c[[2]], d$n, as.list(d)[[3]]

(4) The empty value is unique and does not equal any other symbol:

> identical(c[[2]], d$n)
[1] TRUE

> identical(c[[2]], `a`)
[1] FALSE

(5) The empty symbol cannot be assigned to a standalone variable. If assigned to such a variable, the variable is actually assigned the "missing argument" value:

> x <- d$n
> missing(x)
[1] TRUE
> missing(d$n)
Error in missing(d$n) : invalid use of 'missing'

However, the empty symbol can be assigned to a list slot:

> p <- list(`a`, k=`b`)
> p[[1]] <- d$n
> p$k <- c[[2]]

> identical(p[[1]], d$n)
[1] TRUE

> identical(p[[1]], p[[2]])
[1] TRUE

And it can be passed as a function argument:

> h <- function(x) identical("", d$n)
> h(c[[2]])
[1] TRUE

When passed as a function argument, the argument is not considered to be missing:

> h2 <- function(x) missing(x)
> h2(c[[2]])
[1] FALSE

But compare

> h2(x)
[1] TRUE

(6) The character value of the empty symbol is the empty string:

> identical("", as.character(d$n))
[1] TRUE

(7) There is no primitive function that checks whether a value is the empty symbol. To check whether a value is the empty symbol, its character representation needs to be compared to the empty string:

> is.symbol(d$n) && identical("", as.character(d$n))
[1] TRUE

Appendix

Here are a number of function definitions to facilitate the creation and identification of empty symbols and "missing argument" objects.

> isEmptySymbol
function(x) is.symbol(x) && identical("", as.character(x))

> EmptySymbol
function() (quote(f(,)))[[2]]

> isMissingArgObject
function(x) {
if ("x" %in% names(match.call())) return (missing(x))
stop("An argument must be supplied.") }

> MissingArgObject
function() quote(expr=)

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...