Расчет рёбер социальной сети

Я работаю над открытым набором данных Chess (~ 15500 строк после очистки), и я создаю узлы и ребра. Но то, как я создаю края, требует времени.

Образец моей таблицы узлов:

игрок
1бугри
2а-00
3искья

Образец изображения per_game тибл:

Часть тибла

Как я это делаю:

  1. Я повторяю для каждого узла / игрока в nodes тибл
  2. поиск игр, в которых он играл черными в per_game,
  3. и обмен значениями столбца white_d с участием black_id, меняя победителя в winner столбец (используя swap() метод, который я создал).
  4. Затем с calc_victories() метода, я группирую все игры для конкретного игрока, с каждым противником, с которым он столкнулся, и подсчитываю, сколько раз он выигрывал или проигрывал у оппонента (я сохраняю его в player_result). Пример изображения:
    введите описание изображения здесь
  5. Затем я добавляю player_result с точностью до мелочей, со всеми результатами предыдущих игроков.
  6. Наконец, я удаляю из per_game tibble узел, который я только что обработал, из черных и белых столбцов.

Вот мой код:

for(i in 1:dim(nodes)){
    # Exchange values of white with black column, only where black_id is the specific player
    per_game[per_game$black_id == nodes[[1]][i], c('white_id', 'black_id', 'winner')] <-
        per_game[per_game$black_id == nodes[[1]][i], c('black_id', 'white_id', swap('winner'))]
    
    # Calculate the victories, for each opponent of the specific player
    player_results <- calc_victories(nodes[[1]][i])
    
    # Append the player's matches with the rest.
    all_results <- rbind(all_results, player_results)
    
    # Delete all matches with the specific player, either if he/she is black or white
    per_game <- subset(per_game, white_id != nodes[[1]][i] & black_id != nodes[[1]][i])
}
all_results

Вот функции calc_victories () и своп():

# A method to group the matches for a player, and sum his victories against each opponent
calc_victories <- function(i='-') {
    player_results <- per_game %>% 
        filter(white_id==i | black_id==i) %>% # Finds matches with the specific player
        group_by(white_id, black_id) %>%
        rename(player1=white_id, player2=black_id) %>%
        summarise_at(vars(total_matches), list(victories = sum)) %>% # Summarize total matches
        arrange(desc(victories)) %>% # Sorts descending
        ungroup()

    return (player_results)
}

# A method to change the winner, because of white-black column exchange
swap <- function(winner="draw") {
    if(winner=='black'){
        gets="white"
    } else if(winner=='white'){
        gets="black"
    } else {
        return (winner)
    }
    return(gets)
}

Код выполняется около 5 минут для обработки всех узлов. Я думаю, что это происходит главным образом потому, что я повторяю для каждого узла. Возможно, мне стоит использовать что-то вроде карты, но я не уверен. Спасибо.

0

Добавить комментарий

Ваш адрес email не будет опубликован.