Как сделать мою функцию запросов к БД более эффективной, не жертвуя при этом удобством - PullRequest
0 голосов
/ 15 мая 2018

Я написал функцию для более удобного доступа к базе данных, которую я использую на работе: вместо того, чтобы вводить традиционные команды SQL, я могу просто перечислить имя таблицы в базе данных, и функция автоматически загрузит полную таблицу вR, который я назначаю для фрейма данных.Когда он загружен, некоторые столбцы с типами, такими как дата и логический , отображаются как целое число или символ , поэтому моя функция также определяети перезагружает их.

К сожалению, в последнее время мои запросы выполнялись медленнее, а в некоторых случаях даже не завершались.Я не знаю, происходит ли это из-за проблемы с базой данных или из-за кода, но я действительно контролирую только последнее, поэтому решил, что получу некоторую обратную связь и выясню, смогу ли я сделать некоторые части более эффективными.Одна часть, которую я знаю , неэффективна - это * часть запроса - мне редко нужны все столбцы, но я часто не знаю, какие из них мне понадобятся заранее, и поскольку их многоразличные таблицы, в которые я могу загрузить, * это единственное предложение выбора, которое я знаю, будет работать для всех них.Однако я открыт для любых других оценок эффективности.Я пройдусь по функции:

GetFinderTable <- function(table) {
  if (missing(table))
    stop("ERROR: Table missing")
  if (!table %in% c(*table names*))
    stop("ERROR: Table not found in Finder Database")
  query <- "*"

Первая часть функции выполняет базовую проверку ошибок, чтобы убедиться, что имя таблицы существует и является одной из таблиц в базе данных.Я присваиваю значение * запросу "запрос" - я думал о расширении этого, чтобы обеспечить другие имена столбцов для этой переменной, но это будет очень зависеть от таблицы.

  LoadPackages(c('DBI', 'RMySQL', 'glue', 'magrittr', 'rlist'))
  db <- dbConnect(MySQL(), user = -private-, password = -private-, host = -private-, dbname = -private-)
  df <- dbGetQuery(db, glue('select {query} from {table}'))
  dbDisconnect(db)

LoadPackages это еще одна специальная функция, которую я написал для упрощения управления пакетами - она ​​будет устанавливать, обновлять или присоединять перечисленные пакеты по мере необходимости.Независимо от того, кто запускает этот скрипт, необходимые пакеты будут установлены.следующие три строки фактически запрашивают базу данных.Я использовал клей , потому что это более удобно, но мне интересно, если это менее эффективно по сравнению с paste .

  cols <- apply(df, 2, function(x) (grepl("[0-9][0-9][0-9][0-9]-[0-9][0-9]-[0-9][0-9]$", na.omit(x)) %>% all)) 
  %>% which
  size <- length(cols)
  if (size > 0) {
    if (size == 1)
      df[,cols] %<>% as.Date
    else
      df[,cols] %<>% lapply(as.Date)
  }
  cols <- apply(df, 2, function(x) (grepl("^[0-1]$", na.omit(x)) %>% all)) %>% which %>% 
    list.append(apply(df, 2, function(x) (grepl("False|True", na.omit(x)) %>% all)) %>% which)
  size <- length(cols)
  if (size > 0) {
    if (size == 1)
      df[,cols] %<>% as.logical
    else
      df[,cols] %<>% lapply(as.logical)
   }
  return(df) 
}

Вот где я надеюсь сделать некоторую эффективностьприбыли.Эти следующие несколько строк изолируют столбцы даты (проверяя, соответствуют ли они формату даты R) и логические столбцы (проверяя, содержат ли столбцы исключительно 0 и 1 или «Истина» и «Ложь»).Я случайно обнаружил опасность использования lapply там, где есть только один столбец, который нуждается в переопределении, поэтому у меня условие , если .После преобразования возвращается фрейм данных.

Любая идея о том, как сделать функцию более эффективной, будет принята с благодарностью.Я слишком долго жду завершения этих запросов!

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