2013-08-05 26 views
8

Hãy xem xét các khung dữ liệu sau:Đặt giá trị cột từ một tập hợp các cột khác được lựa chọn bởi một cột chọn trên cơ sở hàng-by-hàng (thực hiện một tra cứu)

TEST <- structure(list(Value = c(NA, NA, NA, NA, NA, NA, NA, NA, NA, NA, NA, NA), 
    Select = structure(c(2L, 1L, 3L, 2L, 2L, 1L, 1L, 
    2L, 1L, 1L, 3L, 3L), .Label = c("A", "B", "C"), class = "factor"), 
    A = c(5L, 5L, 4L, 3L, 4L, 3L, 5L, 3L, 3L, 4L, 5L, 4L), 
    B = c(10L, 8L, 7L, 6L, 3L, 8L, 8L, 7L, 8L, 9L, 11L, 8L), 
    C = c(0L, 1L, 3L, 2L, 0L, 3L, 0L, 2L, 0L, 1L, 1L, 0L)), 
    .Names = c("Value", "Select", "A", "B", "C"), 
    row.names = c(NA, -12L), 
    class = "data.frame") 

Tôi muốn gán một cách hiệu quả các giá trị gia tăng cột, trên cơ sở từng hàng, từ tập hợp các cột A, B và C dựa trên cột Chọn.

Ví dụ: trong hàng 1 Tôi muốn Giá trị bằng với phần tử trong cột B - nghĩa là Giá trị [1] = 10.

phương pháp hiện tại của tôi là sử dụng một vòng lặp for:

for(idx in 1:nrow(TEST)) { 
    TEST$Value[idx] <- TEST[ idx, as.character(TEST$Select[idx]) ] 
} 

Những kết quả trong các đầu ra mong muốn:

 
    Value Select A B C 
1  10  B 5 10 0 
2  5  A 5 8 1 
3  3  C 4 7 3 
4  6  B 3 6 2 
5  3  B 4 3 0 
6  3  A 3 8 3 
7  5  A 5 8 0 
8  7  B 3 7 2 
9  3  A 3 8 0 
10  4  A 4 9 1 
11  1  C 5 11 1 
12  0  C 4 8 0 

Có cách nào hiệu quả hơn hoặc thay thế để làm điều này? Tôi cảm thấy như thế này là một số loại hợp nhất() hoặc hoạt động kiểu nối bảng.

P.S. Tôi đã không hoàn toàn chắc chắn làm thế nào để mô tả hoạt động này - bất kỳ đề xuất cho một câu hỏi/mô tả tốt hơn cũng được chào đón.

+0

RE: PS, I think * lookup * có thể là thuật ngữ thích hợp. – flodel

Trả lời

7

Tôi sẽ sử dụng lập chỉ mục ma trậnmatch. Cách tiếp cận đó là vector hóa, do đó nhanh hơn nhiều so với một vòng lặp for hoặc apply sẽ cung cấp cho bạn:

L <- c("A", "B", "C") 
TEST$Value <- TEST[L][cbind(seq_len(nrow(TEST)), match(TEST$Select, L))] 

Nếu bạn không quen thuộc với ma trận đánh chỉ số, nó là tài liệu bên trong ?"[":

Một hình thức thứ ba của lập chỉ mục là thông qua ma trận số với một cột cho mỗi thứ nguyên: mỗi hàng của ma trận chỉ mục sau đó chọn một phần tử duy nhất của mảng và kết quả là một vector

+0

Thật tuyệt vời, tôi chưa bao giờ thực sự sử dụng lập chỉ mục ma trận trước đây. Bí quyết sử dụng match() cũng thực sự thông minh - đặc biệt là khi nó không thất bại nếu không có cột phù hợp. – Simon

Các vấn đề liên quan