R 匹配向量之间的名称并指定相应的值

R 匹配向量之间的名称并指定相应的值,r,R,这是一个关于R中效率的问题。我有两个带有名称属性的数值向量,我想根据公共名称有效地将一个向量的值分配给另一个向量 例如,第一个向量定义为: set.seed(1); a<-rep(NA,10); names(a)<-1:10; d<-a; # we will need this later a 1 2 3 4 5 6 7 8 9 10 NA NA NA NA NA NA NA NA NA NA 我的问题是:有没有更好更有效的方法?我正在处理更大的向

这是一个关于R中效率的问题。我有两个带有
名称
属性的数值向量,我想根据公共
名称
有效地将一个向量的值分配给另一个向量

例如,第一个向量定义为:

set.seed(1);
a<-rep(NA,10);
names(a)<-1:10;
d<-a;  #  we will need this later 
a

 1  2  3  4  5  6  7  8  9 10 
NA NA NA NA NA NA NA NA NA NA
我的问题是:有没有更好更有效的方法?我正在处理更大的向量,我一直在想,一定有更好的方法来做到这一点

一种更复杂的方法,如:

d[which(names(d) %in% names(b))]<- b
d

1   2   3   4   5   6   7   8   9  10 
"g"  NA  NA  NA "j" "n"  NA  NA "u" "e"  

all.equal(a,d)

[1] "4 string mismatches"
d[其中(名称(d)%in%names(b))]正确答案:

基于@flodel的评论

a[match(names(b), names(a))] <- b
试试这个:

a[names(a) %in% names(b)] <- b[names(a[names(a) %in% names(b)])]

a[names(a)%in%names(b)]我可能会这样做:

a[names(b)] <- b
> a
#   1   2   3   4   5   6   7   8   9  10 
# "e"  NA  NA  NA "u" "n"  NA  NA "g" "j" 
a[intersect(名称(b),名称(a))]a
1   2   3   4   5   6   7   8   9  10 
“e“NA”NA“u”n“NA”NA“g”j”
1为您准备的衬里:

a[as.integer(names(b))]<-b

a[as.integer(names(b))]如果向量名不是按数字顺序排列的呢?我会担心b的名称可能不是a的子集。@user1609452很好。我仍然认为match函数值得一提。不过,我确实喜欢使用intersect的想法——我在自己编写代码时没有想到这点。@user1609452。这不应该引起关注,因为
match
将返回
NA
a[NA]@user1609452。谢谢我测试了
长度(b)==1
。如果较长的
b
包含一个或多个
NA
,它仍然不会抛出错误,但会对
a
产生破坏性影响。请参见第二个解决方案中不需要的
a
<代码>d[名称(d)%in%names(b)]嗯,对我来说不是。当包含
which()
时,它给出了与上面所示相同的结果。请注意,它不同于for-loop后面的
a
。如果两者都被命名,那么,
a[names(b)]@Arun谢谢!这是一个更好的解决方案!当用户1609452注意到
b
不是
a
的子集时,请参见joran的回答。
a[names(b)]只要
names(b)
names(a)
的子集就可以工作。是的,在这种情况下,您只需要在原始长度“a”上进行子集。
a[names(a) %in% names(b)] <- b[names(a[names(a) %in% names(b)])]
a[names(b)] <- b
> a
#   1   2   3   4   5   6   7   8   9  10 
# "e"  NA  NA  NA "u" "n"  NA  NA "g" "j" 
set.seed(45)
a <- rep(NA, 10)
names(a) <- sample(10)
#  7  3  2  9 10  8  1  5  4  6 
# NA NA NA NA NA NA NA NA NA NA 

b <- sample(letters, 5)
names(b) <- sample(1:15, 5)
#   7  14   2   5   3 
# "j" "w" "h" "k" "z" 

len <- length(a)
a[names(b)] <- b
a[1:len]
#   7   3   2   9  10   8   1   5   4   6 
# "j" "z" "h"  NA  NA  NA  NA "k"  NA  NA 
a[intersect(names(b), names(a))] <- b[intersect(names(b), names(a))]
> a
  1   2   3   4   5   6   7   8   9  10 
"e"  NA  NA  NA "u" "n"  NA  NA "g" "j" 
a[as.integer(names(b))]<-b