R 中嵌套 for 循环中的引用元素
Referencing Elements in Nested for loops in R
我正在尝试编写一个循环来对数据帧执行以下操作:
对于 'Name' 列中的每个名称,检查 'Referral' 列中是否存在粗略匹配(通过 agrep() 完成)。如果存在匹配项,请将 'Referral' 列中与名称大致匹配的所有单元格替换为 'referral'。
到目前为止,这是我的代码:
for (i in 1:1000){
for (q in 1:length(agrep(c$Name[i], c$Referal))){
if (length(agrep(c$Name[i], c$Referal)>0)){
c$Referal[agrep(c$Name[i], c$Referal)[q]]<-'panda'
}
}
}
然而,此代码(在 运行 需要 20 分钟后)将 'Referral' 列中的所有单元格替换为 'referral'。我想知道第一行中的 'i' 在整个循环中是否保持不变?显然是一堆笨拙的代码,但我想不出为什么会这样做...
例如:
Name <- c('michael jordan', 'carrot', 'ginger')
Referral <-('internet', 'facebook', 'mike jordan')
df <- data.frame(Name, Referral)
在 运行 调用该函数后,理想情况下 df$Referral[3]=='referral' 将为 TRUE。
您尝试过使用 value=TRUE
选项吗?
照原样,您的代码是 returning 来自 agrep()
的整个向量。使用 value=TRUE
应该只 return 匹配的对象。
编辑:这里有一些代码可以帮助您理解 agrep()
是什么 returning 以及它在您的循环中是如何工作的。
Name <- c('michael jordan', 'carrot', 'ginger')
Referral <- c('internet', 'facebook', 'mike jordan')
df <- data.frame(Name, Referral)
agrep(df$Name[1], df$Referral, max = 5, value = TRUE)
# [1] "mike jordan"
length(agrep(df$Name[1], df$Referral, max = 5, value = TRUE))
# [1] 1
agrep(df$Name[1], df$Referral, max.distance = 0.5)
# integer(0)
df$Referral[agrep(df$Name[1], df$Referral)[1]]
# NULL
for (i in 1:3){
for (q in 1:length(agrep(df$Name[i], df$Referral))){
if (length(agrep(df$Name[i], df$Referral)>0)){
df$Referral[agrep(df$Name[i], df$Referral)[q]] <-'panda'
}
}
}
只是为了更清楚 max
论点的重要性。这里有 3 个例子,请记住 integer(0)
是 R 中的零长度向量。
> agrep(df$Name[1], df$Referral)
integer(0)
> agrep(df$Name[1], df$Referral, max.distance = 0.2)
integer(0)
> agrep(df$Name[1], df$Referral, max.distance = 0.5)
[1] 3
不确定agrep
是否会以您期望的方式为您工作:
agrep('michael jordan', 'mike jordan')
integer(0)
所以我稍微更改了您的数据。 mike jordan
现在在两个向量中:
Name <- c('mike jordan', 'carrot', 'ginger')
Referral <-c('internet', 'facebook', 'mike jordan')
我也把逻辑条件改成了Referral[x] %in% Name
。然后你可以做
library(tidyverse)
newReferral <- map_chr(Referral, ~ifelse(.x %in% Name,'referral', .x))
[1] "internet" "facebook" "referral"
我正在尝试编写一个循环来对数据帧执行以下操作:
对于 'Name' 列中的每个名称,检查 'Referral' 列中是否存在粗略匹配(通过 agrep() 完成)。如果存在匹配项,请将 'Referral' 列中与名称大致匹配的所有单元格替换为 'referral'。
到目前为止,这是我的代码:
for (i in 1:1000){
for (q in 1:length(agrep(c$Name[i], c$Referal))){
if (length(agrep(c$Name[i], c$Referal)>0)){
c$Referal[agrep(c$Name[i], c$Referal)[q]]<-'panda'
}
}
}
然而,此代码(在 运行 需要 20 分钟后)将 'Referral' 列中的所有单元格替换为 'referral'。我想知道第一行中的 'i' 在整个循环中是否保持不变?显然是一堆笨拙的代码,但我想不出为什么会这样做...
例如:
Name <- c('michael jordan', 'carrot', 'ginger')
Referral <-('internet', 'facebook', 'mike jordan')
df <- data.frame(Name, Referral)
在 运行 调用该函数后,理想情况下 df$Referral[3]=='referral' 将为 TRUE。
您尝试过使用 value=TRUE
选项吗?
照原样,您的代码是 returning 来自 agrep()
的整个向量。使用 value=TRUE
应该只 return 匹配的对象。
编辑:这里有一些代码可以帮助您理解 agrep()
是什么 returning 以及它在您的循环中是如何工作的。
Name <- c('michael jordan', 'carrot', 'ginger')
Referral <- c('internet', 'facebook', 'mike jordan')
df <- data.frame(Name, Referral)
agrep(df$Name[1], df$Referral, max = 5, value = TRUE)
# [1] "mike jordan"
length(agrep(df$Name[1], df$Referral, max = 5, value = TRUE))
# [1] 1
agrep(df$Name[1], df$Referral, max.distance = 0.5)
# integer(0)
df$Referral[agrep(df$Name[1], df$Referral)[1]]
# NULL
for (i in 1:3){
for (q in 1:length(agrep(df$Name[i], df$Referral))){
if (length(agrep(df$Name[i], df$Referral)>0)){
df$Referral[agrep(df$Name[i], df$Referral)[q]] <-'panda'
}
}
}
只是为了更清楚 max
论点的重要性。这里有 3 个例子,请记住 integer(0)
是 R 中的零长度向量。
> agrep(df$Name[1], df$Referral)
integer(0)
> agrep(df$Name[1], df$Referral, max.distance = 0.2)
integer(0)
> agrep(df$Name[1], df$Referral, max.distance = 0.5)
[1] 3
不确定agrep
是否会以您期望的方式为您工作:
agrep('michael jordan', 'mike jordan')
integer(0)
所以我稍微更改了您的数据。 mike jordan
现在在两个向量中:
Name <- c('mike jordan', 'carrot', 'ginger')
Referral <-c('internet', 'facebook', 'mike jordan')
我也把逻辑条件改成了Referral[x] %in% Name
。然后你可以做
library(tidyverse)
newReferral <- map_chr(Referral, ~ifelse(.x %in% Name,'referral', .x))
[1] "internet" "facebook" "referral"