Как сравнить каждое значение из столбца из одного df с каждым значением из столбца другого df в R? DFS с разными номерами строк - PullRequest
0 голосов
/ 09 марта 2020

Какой ящик подходит к какой корзине, учитывая также приоритетность ящиков и корзин?

df.boxes имеет следующие столбцы:
boxID - имя коробки
boxX - размер коробки в измерении X
boxY - размер коробки в измерении Y
Важность - какой ящик следует назначить корзине первым. как приоритет - 555 самых важных (с самым высоким приоритетом), 111 наименее важных (с самым низким приоритетом)

df.basket имеет следующие столбцы:
basketID - название корзины
basketX - размер корзины в измерении X
basketY - размер корзины в измерении Y
priorityOfSelection - какая корзина должна быть сначала заполнена коробкой. 1 - наивысший приоритет, 7 - наименьший приоритет

, например, box1 не помещается в корзину с наивысшим приоритетом, она же корзина 1, поэтому она перемещается вниз к следующей корзине с priorityOfSelection «2» и сохраняет его имя в новом столбце "коробки" df.basket.

У меня есть, хотя, сначала я упорядочиваю два фрейма данных на основе их "важности", "priorotyOfSelection" и сравниваю размер блоков с размер корзины и, если есть совпадение, я назначаю имя ящика соответствующей корзине. В этом порядке мышления я пытаюсь создать вложенное для -10 * безуспешно, как вы можете видеть.

Может ли кто-нибудь указать, что и где я делаю неправильно, или направить меня на альтернативный подход, который также был бы высоко оценен?

представ

 df.boxes <-structure(list(boxID = c("box 1", "box 2", "box 3", "box 4", "box 5"), 
                                  boxX = c(600,450, 400, 350, 200), 
                                  boxY = c(600, 400, 450, 500, 300),
                                  importance = c(555, 444, 333, 222, 111) 
                                  ), class = "data.frame", row.names = c(NA, -5L))

df.basket <- structure(list(basketID = c("basket 1", "basket 2", "basket 3","basket 4", "basket 5", "basket 6", "basket 8"), 
                            basketX = c(500,650, 500,200, 450, 500,300),
                            basketY = c(450,650, 500,300,450,500, 300),
                            priorityOfSelection = c(1, 2, 3, 4, 5,6,7) 
                            ), class = "data.frame", row.names = c(NA, -7L))

попытка:

for (i in 1:nrow(df.boxes)){
  for(j in 1:nrow(df.basket)){
  df.basket$box[j] <- ifelse((df.boxes$boxX[i] <= df.basket$basketX[j] | df.boxes$boxY[i] <= df.basket$basketX[j]) & (df.boxes$boxX[i] <= df.basket$basketY[j] | df.boxes$boxY[i] <= df.basket$basketY[j]), 
                                df.boxes$boxID[i], "none")
  }
}

желаемый вывод:
enter image description here

Спасибо очень за ваше время!

Ответы [ 2 ]

1 голос
/ 09 марта 2020

Просто для удовольствия поздняя подача с «чистым for зацикливанием» и if без лишних столбцов.
В предположении, что вы в основном пытаетесь достичь, толкая поля сверху вниз в (упорядоченные по приоритету) корзины (список)

df.basket$box <- NA
for (i in seq.int(df.boxes$boxID)){
  for (j in seq.int(df.basket$basketID)){
    if(is.na(df.basket$box[j])){ 
        if (all( c(df.basket$basketX[j], df.basket$basketY[j]) -
                 c(df.boxes$boxX[i], df.boxes$boxY[i]) >= 0)){
            df.basket$box[j] <- df.boxes$boxID[i] 
  break
        }
    }
  }
}
df.basket$box[is.na(df.basket$box)] <- "none" 
df.basket 

    basketID basketX basketY priorityOfSelection   box
1 basket 1     500     450                   1 box 2
2 basket 2     650     650                   2 box 1
3 basket 3     500     500                   3 box 3
4 basket 4     200     300                   4 box 5
5 basket 5     450     450                   5  none
6 basket 6     500     500                   6 box 4
7 basket 8     300     300                   7  none

Конечно, не такой элегантный, как решение '@Allan Cameron', но также возможный подход, если вы хотите gr asp the for l oop подход, с которого вы начали в своей собственной попытке немного лучше.

1 голос
/ 09 марта 2020

Если вы установили дополнительный столбец в df.boxes для записи того, был ли ящик «использован» или нет, вы можете сделать это следующим образом:

df.basket$box <- character(nrow(df.basket))
df.boxes$used <- logical(nrow(df.boxes))

for(i in sort(df.basket$priorityOfSelection))
{
  fits <- which(df.boxes$boxX <= df.basket$basketX[i] &
                df.boxes$boxY <= df.basket$basketY[i] &
                df.boxes$used == FALSE)

  df.basket$box[which(df.basket$priorityOfSelection == i)] <- 
    paste("box", fits[which.max(df.boxes$importance[fits])])
  df.boxes$used[fits[which.max(df.boxes$importance[fits])]] <- TRUE
}

df.basket$box[df.basket$box == "box "] <- "none"

df.basket
#>   basketID basketX basketY priorityOfSelection   box
#> 1 basket 1     500     450                   1 box 2
#> 2 basket 2     650     650                   2 box 1
#> 3 basket 3     500     500                   3 box 3
#> 4 basket 4     200     300                   4 box 5
#> 5 basket 5     450     450                   5  none
#> 6 basket 6     500     500                   6 box 4
#> 7 basket 8     300     300                   7  none

Создано в 2020- 03-09 представьте пакет (v0.3.0)

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...