Refer to primitive operator in R [duplicate] - r

This question already has answers here:
Making a string concatenation operator in R
(5 answers)
Closed 2 years ago.
I'm a big fan of the + operator for string concatenation in Python. I would like to extend/customize the + operator to do the same thing in R.
Here's what I have so far:
`+` <- function(a, b){
if(is.numeric(a)){
sum(a, b)
}else{
paste0(a, b)
}
This works pretty well, but in some speed tests, performs poorly compared to the original/primitive +. So, how can I refer to the primitive + instead of sum() in the second line of the function? If I just use +, of course R gives me a node stack overflow from infinite recursion.

(The answer offered in the duplicate question is another alternative, cleaner perhaps in that it does not add another function.)
Save the primitive as another function. Here I'll use a "special" function %plus% (so that it can be inlined), but it could be simply plus if you'd prefer.
`%plus%` <- `+`
`+` <- function(e1, e2) if (is.numeric(e1)) `%plus%`(e1, e2) else paste0(e1, e2)
1+2
# [1] 3
'a'+'b'
# [1] "ab"

Related

Julia: Check if elements from one vector are within another vector [duplicate]

This question already has answers here:
Vectorized "in" function in julia?
(5 answers)
Closed 5 years ago.
I would like to check if the elements in one vector are contained within another vector. In R there is the operator %in%.
For example the operator would do the following:
[1,3,5,7,9,4] %in% [1,2,4,5,8,9,10,11]
# [true,false,true,false,true,true]
I can easily write my own only I am trying not to reinvent the wheel.
Probably not so nice, but you could do:
julia> [1,3,5,7,9,4] .∈ [[1,2,4,5,8,9,10,11]]
6-element BitArray{1}:
true
false
true
false
true
true
There are a number of built-ins that do something similar. indexin gives you the indices in b where the elements of a are found (0 if it is not there - this is similar to R's match). setdiff gives you the elements in a that are not in b. It is likely you'll be able to do what you want with these - constructing temporary boolean arrays for filtering is not so ideomatic in julia as in R, as it generally creates an extra, unnecessary allocation.
You could use an anonymous function : map(x -> x in [1,2,4,5,8,9,10,11] ,[1,3,5,7,9,4])
Or a comprehension : [x in [1,2,4,5,8,9,10,11] for x = [1,3,5,7,9,4]]

If `[` is a function for subsetting in R, what is `]`?

I'm reading the advanced R introduction by Hadley Wickham, where he states that [ (and +, -, {, etc) are functions, so that [ can be used in this manner
> x <- list(1:3, 4:9, 10:12)
> sapply(x, "[", 2)
[1] 2 5 11
Which is perfectly fine and understandable. But if [ is the function required to subset, does ] have another use rather than a syntactical one?
I found that:
> `]`
Error: object ']' not found
so I assume there is no other use for it?
This is the fundamental difference between syntax and semantics. Semantics require that — in R — things like subsetting and if etc are functions. That’s why R defines functions `[`, `if` etc.
And then there’s syntax. And R’s syntax dictates that the syntax for if is either if (condition) expression or if (condition) expression else expression. Likewise, the syntax for subsetting in R is obj[args…]. That is, ] is simply a syntactic element and it has no semantic equivalent, no corresponding function (same as else).
To make this perhaps even clearer:
[ and ] are syntactic elements in R that delimit a subsetting expression.
By contrast, `[` (note the backticks!) is a function that implements the subsetting operation.
Somehow though, I was expecting ] to be a syntactical element, by default: indexing from the end. So I define it myself in my code:
"]" <- function(x,y) if (y <= length(x)) x[length(x)+1-y] else NA
With the given example, then:
sapply(x, "]", 1)
[1] 3 9 12
sapply(x, "]", 2)
[1] 2 8 11

How to "rollback" after doing `+` = `-`?

Main Question
I did
> `+` = `-`
> 5 + 2
[1] 3
How can I "rollback" without restarting the console? Doing
> `+` = sum
of course, restores one function of + but not all. For example
> c(3,4) + c(1,2)
[1] 10
How could I restore other functions of +?
Extra related questions
Is there a name for this "kind of assignment" or the kind of functions that "+" and "-" represent?
What terms can be used to differentiate the function "+" from the function "%+%" that one could create doing
`%+%` = function(x,y){print(paste(x,"+",y,"=",x+y))}
rm() removes an object from your workspace.
rm(`+`)
will remove your custom definition that masks the built-in function.
There is nothing special about the assignment you did. As nrussell points out, infix operators (aka binary operators) are generally possible to define by wrapping them in percent signs. The basic math ones (+, -, *, /, ^, even = and <- and logical operators, ==, |, ||, &, &&, <, etc.) are special in that the parser knows they're binary operators even without being wrapped in %. You can see ?Arithmetic (alias ?"+") and ?base::Ops for more details.
You can override this by fully qualifying the function in reassignment:
`+` = `-`
5 + 2
#[1] 3
`+` <- base::`+`
5 + 2
#[1] 7
It's probably better to just rm the new function though, as Gregor suggests, otherwise you will just have extra object floating around your environment needlessly.
Functions such as +, -, *, etc., and even %+% are called infix operators. The difference is that the former are built into the R language (they are primitives), and therefore do not need to be wrapped in % % to avoid generating a parsing error.

The function of parentheses (round brackets) in R

How does R interpret parentheses? Like most other programming languages these are built-in operators, and I normally use them without thinking.
However, I came across this example. Let's say we have a data.table in R, and I would like to apply a function on it's columns. Then I might write:
dt <- data.table(my_data)
important_cols <- c("col1", "col2", "col5")
dt[, (important_cols) := lapply(.SD, my_func), .SDcols = important_cols]
Obviously I can't neglect the parentheses:
dt[, important_cols := lapply(.SD, my_func), .SDcols = important_cols]
as that would introduce a new object called important_cols to my data.table, instead of modifying my existing columns in place.
My question is, why does putting ( ) around the vector "expand" it?
This question can probably better phrased and titled. But then I would have probably found the answer by Googling if I knew the terminology to employ while asking it, hence I'm here.
While we're on that topic, if someone could point out the differences between [ ], { }, etc., and how they should be used, that would be appreciated too :)
A special feature of R (compared to e.g. C++) is that the various parentheses are actually functions. What this means is that (a) and a are different expressions. The second is just a, while the first is the function ( called with an argument a. Here are a few expressions trees for you to compare:
as.list(substitute( a ))
#[[1]]
#a
as.list(substitute( (a) ))
#[[1]]
#`(`
#
#[[2]]
#a
as.list(substitute( sqrt(a) ))
#[[1]]
#sqrt
#
#[[2]]
#a
Notice how similar the last trees are - in one the function is sqrt, in the other it's "(". In most places in R, the "(" function doesn't do anything, it just returns the same expression, but in the particular case of data.table, it is "overridden" (in quotes because that's not exactly how it's done, but in spirit it is) to do a variety of useful operations.
And here's one more demo to hopefully cement the point:
`(` = function(x) x*x
2
#[1] 2
(2)
#[1] 4
((2))
#[1] 16

Meaning of Symbol %>% in R [duplicate]

This question already has an answer here:
What does %>% mean in R [duplicate]
(1 answer)
Closed 8 years ago.
I am an entry level R user.May be this question sound like easy but it will be great if some one can help .
what is the meaning of this symbol in R-coding ...
%>%
Thank you
%>% is most commonly used as an operator for the popular dplyr package
It can be used to chain code together. It is very useful when you are performing several operations on data, and don’t want to save the output at each intermediate step.
%>% means whatever you want it to mean, in Base R anyway:
> %>%
Error: unexpected SPECIAL in "%>%"
(which means that symbol is not defined.)
Binary operators are ones that have an input from the left and from the right of the operator, just like *, + etc. You use them as you would mathematically like a * b, which R turns into the call '*'(a, b). R allows you to add your own binary operators via the %foo% syntax, with foo replace by whatever you want, as long as it hasn't already been used by R, which includes %*% and %/% for example.
`%foo%` <- function(x, y) paste("foo", x, "and foo", y)
> 1 %foo% 2
[1] "foo 1 and foo 2"
%>% takes on a specific and well-defined meaning once you load the magrittr R package for example, where it is used as a pipe operator might be in a Unix shell to chain together a series of function calls.

Resources