我有两个变量(即):
a <- 1 b <- 2
我想交换它们的值。是否有任何内置的R函数,能够执行该操作?或者有其他优雅的方法,而不使用第三个(临时)变量?
**注意:**如果可能,适用于字符串或其他数据类型。
7lrncoxx1#
有一个通用的解决方案或“技巧”:
a <- 1 b <- 2 a <- a + b b <- a - b a <- a - b
这里有一个有用的链接,解释了很多:xor-trick
svdrlsy42#
对于整数,可以使用
a = a + b b = a - b a = a - b
对于弦来说这是可行的
a <- "one" b <- "two" a <- paste(a,b, sep = "") b <- substr(a,0,nchar(a) - nchar(b)) a <- substr(a,nchar(b) + 1, nchar(a)) > a # two > b # one
bvjxkvbb3#
在基本包中有太多函数的好处是:总有办法去做一些事,即使是个坏主意。
list2env(list(a = b, b = a), envir = .GlobalEnv)
不管a和b的类是什么,这都是有效的。这是个坏主意
a
b
gajydyqb4#
开始
A = 9 B = 5 A = A + B
然后
A is 14 B is 5 B = A - B
A is 14 B is 9 A = A - B
结果:A(5)现在是BB(9)现在是A不是真的简单,然后只是使用第三个变量,但我的作品!
axr492tv5#
虽然前面的答案都很好很漂亮,但它们都占用了太多我喜欢的空间!所以我在C中提出了一个更整洁的解决方案:
a = (b - a) + (b = a);
它不能处理字符串,但整数和浮点数都可以。它是这样工作的:
int a = 5, b = 7; a = (b - a) + (b = a); /* turns into */ a = (7 - 5) + (b = 5); /* b is now 5 */ a = 2 + 5; /* a is now 7 */
这里的关键是解析表达式的顺序(从左到右)。因此,表达式中第一次出现的 b 被替换为 b 的原始值,只有在此之后,b 才被分配给 a。我知道这是一个古老的问题,而且已经有了答案,但也许这对外面的人会有用
gstyhher6#
根据Nathan的帖子,为了在运行环境中保持变量交换:
x <- 10 y <- 20 list2env(list(x=y, y=x), envir=as.environment(environment())) print(x) print(y)
fxnxkyjh7#
据我所知,没有内置函数可以做到这一点,也没有通用的方法可以在没有第三个变量的情况下交换两个变量。但是,如果您正在寻找一个至少可以减少代码重复的函数,则以下内容可能会有所帮助:
swap <- function(x,y) { eval( parse( text = paste( "swap_unique_var_a<-", substitute(x), ";", substitute(x), "<-", substitute(y), ";", substitute(y), "<-swap_unique_var_a") ), env=parent.frame() ) }
然后,您可以按如下方式使用它:
a<-1; b<-2; swap(a,b) print(a); print(b)
函数swap()的两个参数引用本地帧中的两个变量,然后交换它们,从而创建一个临时变量。swap()功能的当前限制/问题:
swap()
parent.frame()
x
y
也许可以使函数更健壮,但我有点担心对性能的影响,特别是在解释性语言中,如R,没有等效的内联。如果有兴趣/时间,我将测试性能,看看是否有可能有一个更健壮的版本。
xxslljrj8#
你可以在list中临时存储值,也可以在其中进行赋值。但是我不推荐这种方式,只是为了展示另一种可能性。
list
a <- 1 b <- 2 b <- list(a, a <- b)[[1]] a #[1] 2 b #[1] 1
使用临时变量可能更容易阅读,并且可能更高效。
a <- 1 b <- 2 . <- a a <- b b <- . rm(.) a #[1] 2 b #[1] 1
8条答案
按热度按时间7lrncoxx1#
有一个通用的解决方案或“技巧”:
这里有一个有用的链接,解释了很多:xor-trick
svdrlsy42#
对于整数,可以使用
对于弦来说这是可行的
bvjxkvbb3#
在基本包中有太多函数的好处是:总有办法去做一些事,即使是个坏主意。
不管
a
和b
的类是什么,这都是有效的。这是个坏主意gajydyqb4#
开始
然后
然后
结果:
A(5)现在是B
B(9)现在是A
不是真的简单,然后只是使用第三个变量,但我的作品!
axr492tv5#
虽然前面的答案都很好很漂亮,但它们都占用了太多我喜欢的空间!
所以我在C中提出了一个更整洁的解决方案:
它不能处理字符串,但整数和浮点数都可以。
它是这样工作的:
这里的关键是解析表达式的顺序(从左到右)。因此,表达式中第一次出现的 b 被替换为 b 的原始值,只有在此之后,b 才被分配给 a。
我知道这是一个古老的问题,而且已经有了答案,但也许这对外面的人会有用
gstyhher6#
根据Nathan的帖子,为了在运行环境中保持变量交换:
fxnxkyjh7#
据我所知,没有内置函数可以做到这一点,也没有通用的方法可以在没有第三个变量的情况下交换两个变量。
但是,如果您正在寻找一个至少可以减少代码重复的函数,则以下内容可能会有所帮助:
然后,您可以按如下方式使用它:
函数
swap()
的两个参数引用本地帧中的两个变量,然后交换它们,从而创建一个临时变量。swap()
功能的当前限制/问题:parent.frame()
中创建的,这是您调用swap()
的地方。x
和y
在parent.frame()
环境中,因此全局环境中的变量在parent.frame()
环境中重新创建。也许可以使函数更健壮,但我有点担心对性能的影响,特别是在解释性语言中,如R,没有等效的内联。
如果有兴趣/时间,我将测试性能,看看是否有可能有一个更健壮的版本。
xxslljrj8#
你可以在
list
中临时存储值,也可以在其中进行赋值。但是我不推荐这种方式,只是为了展示另一种可能性。使用临时变量可能更容易阅读,并且可能更高效。