R 相当于Mathematica';哪个

R 相当于Mathematica';哪个,r,rscript,R,Rscript,Mathematica的函数是广义的,如果: 哪个[测试1,值1,测试2,值2,…] 依次计算每个test\u i,返回与第一个生成True的值相对应的值 这不过是一种从嵌套的简单if-else测试的长序列中去除多余语法的简便方法 R是否有一个等价函数 顺便说一句,我知道我总是可以做这样的事情 if (test_1) value_1 else if (test_2) value_2 else ... value_n else default 或者,相当于 if (test_1) value_

Mathematica的函数是广义的
,如果

哪个[测试1,值1,测试2,值2,…]

依次计算每个
test\u i
,返回与第一个生成
True
的值相对应的

这不过是一种从嵌套的简单if-else测试的长序列中去除多余语法的简便方法

R是否有一个等价函数


顺便说一句,我知道我总是可以做这样的事情

if (test_1) value_1 else if (test_2) value_2 else ... value_n else default
或者,相当于

if (test_1) value_1 else
if (test_2) value_2 else
            ...
if (test_n) value_n else
            default
…但是,正如我已经提到的,与
Which
相比,嵌套的
if-else
语句引入了许多多余的语法

而且,我知道

ifelse(t_1, v_1, ifelse(t_2, v_2, ..., ifelse(t_n, v_n, default)...))
…但是结果对测试的形状很敏感,因此它并不严格等同于嵌套的
if-else
语句

最后,R的
switch
语句与我所寻找的类似,它封装了一系列测试的调度,但这并不完全相同。在

switch(expr,
       case_1 = value_1,
       case_2 = value_2,
       ...
       case_n = value_n,
       default)

…这些测试都是将
expr
案例i
进行相等比较,而在
Which
等中,测试是任意布尔表达式。

根据Mathematica帮助

其中[test1,value1,test2,value2,…]依次计算每个testi,返回与第一个生成True的值相对应的值i

我们可以在R中执行此操作,即获得与计算结果为true的第一个表达式的位置相对应的值,如下所示:

1。计算所有表达式的简单版本:

values = c("value1", "value2", "value3", "value4", "value5", "value6", "value7")
expressions = c(1==2, 1==3, 1==1, 1==4, T==F, F==T, T==T)
values[which.max(expressions)]
# [1] "value3"
尽管如此,如果所有表达式都不为true,which.max将返回第一个false,因此我们也应该检查这一点

if (any(expressions))  values[which.max(expressions)] else NA
2。“短路”的版本

然而,上述行为与Mathematica有一个区别:
在Mathematica短路中,它只计算找到第一个真值所需的尽可能多的表达式。如果表达式在计算上很昂贵或存在速度瓶颈,那么我们也可能希望在R中复制这种行为。我们可以使用短路的
位置
eval(parse)
相结合来实现这一点,以确保我们在准备测试表达式之前不会对表达式求值

values = c("value1", "value2", "value3", "value4", "value5", "value6", "value7")
expressions = c("1==2", "1==3", "1==1", "1==4", "T==F", "F==T", "T==F")

values[Position(function(text) eval(parse(text=text)), expressions, T)]

根据Mathematica的帮助

其中[test1,value1,test2,value2,…]依次计算每个testi,返回与第一个生成True的值相对应的值i

我们可以在R中执行此操作,即获得与计算结果为true的第一个表达式的位置相对应的值,如下所示:

1。计算所有表达式的简单版本:

values = c("value1", "value2", "value3", "value4", "value5", "value6", "value7")
expressions = c(1==2, 1==3, 1==1, 1==4, T==F, F==T, T==T)
values[which.max(expressions)]
# [1] "value3"
尽管如此,如果所有表达式都不为true,which.max将返回第一个false,因此我们也应该检查这一点

if (any(expressions))  values[which.max(expressions)] else NA
2。“短路”的版本

然而,上述行为与Mathematica有一个区别:
在Mathematica短路中,它只计算找到第一个真值所需的尽可能多的表达式。如果表达式在计算上很昂贵或存在速度瓶颈,那么我们也可能希望在R中复制这种行为。我们可以使用短路的
位置
eval(parse)
相结合来实现这一点,以确保我们在准备测试表达式之前不会对表达式求值

values = c("value1", "value2", "value3", "value4", "value5", "value6", "value7")
expressions = c("1==2", "1==3", "1==1", "1==4", "T==F", "F==T", "T==F")

values[Position(function(text) eval(parse(text=text)), expressions, T)]

您可以编写自己的函数,该函数可以用作此类控制结构。下面是基于
match.call
支持延迟求值的事实。(见接受的答复):


which.val您可以编写自己的函数,该函数可以用作此类控制结构。下面是基于
match.call
支持延迟求值的事实。(见接受的答复):



which.val@JohnColeman:AFAICT,案例i
必须是标签;它们不能是任意的表达式。。。(我可能错了)@kjo你是对的。@ZheyuanLi:尽管它们的名字不同,R的
函数和Mathematica的
函数做的事情却截然不同。@ZheyuanLi:我很后悔问了这个问题。如果我怀疑这个简单的问题会引起如此多的混乱和反对(即反对票),我就不会问。我很乐意删除它,但它已经得到了一些答案。@JohnColeman:因为,在aict中,
case\u I
必须是标签;它们不能是任意的表达式。。。(我可能错了)@kjo你是对的。@ZheyuanLi:尽管它们的名字不同,R的
函数和Mathematica的
函数做的事情却截然不同。@ZheyuanLi:我很后悔问了这个问题。如果我怀疑这个简单的问题会引起如此多的混乱和反对(即反对票),我就不会问。我很乐意删除它,但它已经得到了一些答案。非常感谢。我不知道R在用户定义函数中支持惰性计算。太好了。问题:你不想
返回(eval(子句[[i+1]])
?你是对的。我用常量值测试了它,它工作正常,但您不希望返回未赋值的表达式。我切换了我的示例,使返回值看起来像
x+10
,而不仅仅是
10
,等等。我的代码没有返回预期的值。我会编辑。谢谢。对不起,还有一件事需要解决:evals需要
envir=parent.frame()
;否则,如果我从另一个函数中调用该函数,就会出现错误。(关于
eval
的文档说
envir
默认为
parent.frame()
,所以我不完全理解为什么我需要明确指定它…@kjo你又对了。这是