如何在向量内交换(转换)值

Gil*_*esh 11 swap r vector

vetA <- c(1,2,1,2,1,3,4,1,2,3,2,1,4)
Run Code Online (Sandbox Code Playgroud)

有什么可能,所以我可以进行以下交换?交换:

  • 1 -->3
  • 2 -->4
  • 3 -->2
  • 4 -->1

我试过这个:

vetB <- as.factor(vetA)
levels(vetB) <- c(3,4,2,1)
vetA <- as.integer(vetB)

# because
print(vetB)
# [1] 3 4 3 4 3 2 1 3 4 2 4 3 1
#Levels: 3 4 2 1
Run Code Online (Sandbox Code Playgroud)

它没用.你能帮我个忙吗?

www*_*www 9

如果在将因子向量转换为整数之前将其转换为字符,则代码将起作用.请注意,factor在内部存储为整数,因此as.integer(vetB)将返回其整数级别.

vetA <- c(1,2,1,2,1,3,4,1,2,3,2,1,4)

vetB <- as.factor(vetA)
levels(vetB) <- c(3,4,2,1)
vetA <- as.integer(as.character(vetB))
vetA
# [1] 3 4 3 4 3 2 1 3 4 2 4 3 1
Run Code Online (Sandbox Code Playgroud)


Sti*_*ibu 9

您可以创建一个查找表:

vetA <- c(1,2,1,2,1,3,4,1,2,3,2,1,4)
lookup <- setNames(c(3, 4, 2, 1), 1:4)
lookup[vetA]
## 1 2 1 2 1 3 4 1 2 3 2 1 4 
## 3 4 3 4 3 2 1 3 4 2 4 3 1
Run Code Online (Sandbox Code Playgroud)

lookup是新值,而名称设置为旧值.然后,您可以使用向量vetA作为索引来选择新值.

由于您替换的值很简单c(1, 2, 3, 4),因此实际上不需要显式设置名称,您只需使用即可获得相同的结果

c(3, 4, 2, 1)[vetA]
## [1] 3 4 3 4 3 2 1 3 4 2 4 3 1
Run Code Online (Sandbox Code Playgroud)

但是,上面的解决方案也适用于您替换的值不仅仅是整数序列的情况.


Flo*_*ian 8

一种可能的选择是使用match:

vetA <- c(1,2,1,2,1,3,4,1,2,3,2,1,4)
old=c(1,2,3,4)
new=c(3,4,2,1)
new[match(vetA,old)]
Run Code Online (Sandbox Code Playgroud)

输出:

3 4 3 4 3 2 1 3 4 2 4 3 1
Run Code Online (Sandbox Code Playgroud)

希望这可以帮助!

  • 它没有`match()`,因为你要替换的值只是`1:4`.在大多数其他情况下(例如,当值不是数字时,或者对于从1开始的任何其他值开始的整数序列),它只适用于`match()`. (4认同)

989*_*989 5

你可以干脆做

new[order(old)][vetA]

# [1] 3 4 3 4 3 2 1 3 4 2 4 3 1
Run Code Online (Sandbox Code Playgroud)

哪里

vetA <- c(1,2,1,2,1,3,4,1,2,3,2,1,4)
old <- c(1,2,3,4)
new <- c(3,4,2,1)
Run Code Online (Sandbox Code Playgroud)

注:本会工作,以及接受的答案被@弗洛里安-即使该向量old排序.在这种情况下,其他两个答案将不起作用.例如,如果

old <- c(3,2,1,4)
new <- c(3,4,2,1)
Run Code Online (Sandbox Code Playgroud)