ใน R ให้ใช้ if loop กับ agrep เพื่อกำหนดค่า

รายการรูปแบบดูเหมือนว่า:

pattern <- c('aaa','bbb','ccc','ddd')

X มาจาก df ดูเหมือนว่า:

df$X <- c('aaa-053','aaa-001','aab','bbb')

สิ่งที่ฉันพยายามทำ: ใช้ agrep เพื่อค้นหาชื่อที่ตรงกันในรูปแบบตาม df$X จากนั้นกำหนดค่าให้กับคอลัมน์ที่มีอยู่ 'column2' ตามผลลัพธ์ที่ตรงกัน ตัวอย่างเช่น หาก 'aaa-053' ตรงกับ 'aaa' ดังนั้น 'aaa' จะเป็นค่าใน 'column2' หากไม่ตรงกัน ให้ส่งคืน na ในคอลัมน์นั้น

for (i in 1:length(pattern)) {
 match <- agrep(pattern, df$X, ignore.case=TRUE, max=0)
 if agrep = TRUE {
   df$column2 <- pattern
 } else {df$column2 <- na
 }
}

คอลัมน์ในอุดมคติ 2 ใน df ดูเหมือนว่า:

'aaa','aaa',na,'bbb'

person onemikeone    schedule 19.03.2021    source แหล่งที่มา
comment
คุณคิดว่าจะเกิดอะไรขึ้นเมื่อ aaa ตรงกับ aab ของคุณ   -  person r2evans    schedule 19.03.2021


คำตอบ (1)


agrep โดยตัวมันเองไม่ได้ให้อะไรคุณมากนักในการพิจารณาว่าจะใช้อันไหนเมื่อจับคู่หลายรายการ ตัวอย่างเช่น

agrep(pattern[1], df$x)
# [1] 1 2 3

ซึ่งสมเหตุสมผลสำหรับสองค่าแรก แต่ค่าที่สามไม่อยู่ในค่าที่คุณคาดหวัง ในทำนองเดียวกัน ก็เป็นไปได้ที่ระบบอาจเลือกหลายรูปแบบสำหรับสตริงที่กำหนด

นี่เป็นทางเลือกอื่น:

D <- adist(pattern, df$x, fixed = FALSE)
D
#      [,1] [,2] [,3] [,4]
# [1,]    0    0    1    3
# [2,]    3    3    2    0
# [3,]    3    3    3    3
# [4,]    3    3    3    3
D[D > 0] <- NA
D
#      [,1] [,2] [,3] [,4]
# [1,]    0    0   NA   NA
# [2,]   NA   NA   NA    0
# [3,]   NA   NA   NA   NA
# [4,]   NA   NA   NA   NA
apply(D, 2, function(z) which.min(z)[1])
# [1]  1  1 NA  2
pattern[apply(D, 2, function(z) which.min(z)[1])]
# [1] "aaa" "aaa" NA    "bbb"
person r2evans    schedule 19.03.2021
comment
ฉันคิดว่าวิธีนี้ใช้ได้กับข้อมูลตัวเลข แต่เงื่อนไขของฉันขึ้นอยู่กับค่าอักขระ นั่นคือสาเหตุที่ฉันพยายามใช้ agrep ในตอนแรก - person onemikeone; 29.03.2021
comment
ฉันไม่รู้ว่าคุณหมายถึงอะไร agrep ใช้ได้กับสตริง ไม่ใช่ตัวเลข เช่นเดียวกับ adist ประเด็นของคำตอบนี้คือ (1) แสดงให้เห็นว่าสมมติฐานของคุณในการจับคู่นัดเดียวมีข้อบกพร่อง และ (2) เสนอแนะวิธีการเพื่อพยายามบรรเทาข้อบกพร่องนั้น ส่วนที่เป็นตัวเลขของคำตอบนี้ให้ค้นหาระยะห่างระหว่างสตริงที่น้อยที่สุด ซึ่งควรระบุการจับคู่ที่ดีที่สุด หากคุณต้องการหลีกเลี่ยงตัวเลข ฉันขอแนะนำให้คุณใช้ข้อมูลที่ไม่เคยมีความเสี่ยงที่จะทับซ้อนกันเหมือนตัวอย่างของคุณ หรือใช้วิธีคิดที่ใช้งานง่ายกว่าการจับคู่สตริงแบบคลุมเครือ ขอให้โชคดี! - person r2evans; 29.03.2021
comment
มุมมองอื่น: เมื่อพิจารณาจากข้อมูลตัวอย่างของคุณ สิ่งนี้จะให้คำตอบที่คุณคาดหวังในรูปแบบสตริง มีเงื่อนไขหรือคุณสมบัติอื่นของข้อมูลที่ทำให้โค้ดนี้ทำงานได้ไม่ดีหรือไม่? มีข้อมูลอื่นที่ไม่สามารถใช้งานได้หรือไม่? หากข้อมูลจริงของคุณล้มเหลว คุณจะไม่สามารถคาดหวังอะไรได้ดีไปกว่านี้หากคุณไม่ปรับปรุงคำถามของคุณให้รวมข้อมูลตัวอย่างที่เป็นตัวแทนมากขึ้น - person r2evans; 29.03.2021