[英]Efficient way to iterate over two lists (nested loop alternative)
我有兩個數據幀,SCR和SpecificSpecies。 SCR中的項目名稱部分包含“特定物種”中列出的物種。
SpecificSpecies$Species
S cerevisiae
Daucus carota
SCR$MESH_HEADINGS
tetracycline CMT-3
zrg17 protein, S cerevisiae
EP4 glycoprotein, Daucus carota
我正在嘗試獲取SCR的子集,該子集僅包含那些沒有任何匹配種類的條目。 在上述情況下,該列表僅
tetracycline CMT-3.
我學會的方法是使用嵌套循環,將SCR中的每個條目與SpecificSpecies中的每個條目進行比較。 如果找不到匹配項,請將SCR行追加到新表中:
For each row in SCR {
SpeciesNumber <- 1
match <-NULL
while ((is.null(match)) & (SpeciesNumber < length(SpecificSpecies$Species))) {
if (grepl(SpecificSpecies$Species[SpeciesNumber], SCR[row,]$MESH_HEADING)){
match <- TRUE}
SpeciesNumber <- SpeciesNumber + 1}
if ((is.null(match) & SpeciesNumber == length(SpecificSpecies$Species)) {
speciesNoMatch = rbind(speciesNoMatch, SCR[row])}
}}
但是,這非常慢,SCR中有65,000個條目,SpecificSpecies中有1500個條目。 有沒有辦法像這樣用lapply嵌套? 還是其他一些我不熟悉的功能將對您有所幫助?
我確定這是很糟糕的代碼。 我是一名醫學圖書館員,有時不得不使用R進行數據分析,所以我的編程技能非常有限,但是只要我的解決方案最終可行,它通常是丑陋還是效率低下,這並不重要。 我知道一定有更好的方法可以做到這一點; 原諒我不了解可能是一個簡單解決方案的事情。
我認為!(%in%)
可以解決問題:
SpecificSpecies <- data.frame(
Species = c("S cerevisiae", "Daucus carota"),
stringsAsFactors = FALSE
)
SCR <- data.frame(
MESH_HEADINGS = c("tetracycline CMT-3", "zrg17 protein", "S cerevisiae",
"EP4 glycoprotein", "Daucus carota"),
stringsAsFactors = FALSE
)
SCR[!(SCR$MESH_HEADINGS %in% SpecificSpecies$Species), , drop = FALSE]
# MESH_HEADINGS
# 1 tetracycline CMT-3
# 2 zrg17 protein
# 4 EP4 glycoprotein
, , drop = ...
不是錯字。 第一個,
確保返回所有列/變量。 第二個, drop = FALSE
確保返回的結果仍然是數據幀。
好吧,我剛剛注意到你正在尋找grep
與Species
。 下面的代碼應該工作:
SpecificSpecies <- data.frame(
Species = c("S cerevisiae", "Daucus carota"),
stringsAsFactors = FALSE
)
SCR <- data.frame(
MESH_HEADINGS = c("tetracycline CMT-3",
"zrg17 protein, S cerevisiae",
"EP4 glycoprotein, Daucus carota"),
stringsAsFactors = FALSE
)
matching <- lapply(SpecificSpecies$Species, function(x) {
grep(x, SCR$MESH_HEADINGS)
})
SCR[-(unlist(matching)), ]
# MESH_HEADINGS
# 1 tetracycline CMT-3
lapply()
使用匿名函數來識別模式匹配。 它遍歷每個物種,並將其與每個SCR$MESH_HEADINGS
項目進行比較。 它返回匹配索引的列表。
在我們首先unlist
匹配索引以使其與子集功能兼容之后,子集( []
)會簡單地刪除匹配索引( -
)。
大意:
在SpecificSpecies上執行循環,因為它的行較少。 由於SCR數據幀將減少,因此需要遞歸執行,因此循環每次只處理較少的數據。
通常,軟件包data.table
或plyr
提高性能。 這里是data.table
的解決方案
library(data.table)
SpecificSpecies <- data.frame(Species = c("S cerevisiae", "Daucus carota"),stringsAsFactors = FALSE)
SCR <- data.frame(MESH_HEADINGS = c("tetracycline CMT-3", "zrg17 protein, S cerevisiae","EP4 glycoprotein Daucus carota"),stringsAsFactors = FALSE)
dt_temp <- data.table(SCR)
for (species in SpecificSpecies$Species) {
dt_temp <- dt_temp[!grepl(species,dt_temp$MESH_HEADINGS), ]
}
dt_result <- dt_temp
dt_result
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.