R Y*_*oda 12
真的很晚,我的回答,但也许还有帮助...
在DBI/odbc包中没有单一的功能(我知道),但你可以使用准备好的更新语句复制更新行为(它应该比RODBC更快,sqlUpdate因为它将参数值作为批处理发送到SQL服务器:
library(DBI)
library(odbc)
con <- dbConnect(odbc::odbc(), driver="{SQL Server Native Client 11.0}", server="dbserver.domain.com\\default,1234", Trusted_Connection = "yes", database = "test") # assumes Microsoft SQL Server
dbWriteTable(con, "iris", iris, row.names = TRUE) # create and populate a table (adding the row names as a separate columns used as row ID)
update <- dbSendQuery(con, 'update iris set "Sepal.Length"=?, "Sepal.Width"=?, "Petal.Length"=?, "Petal.Width"=?, "Species"=? WHERE row_names=?')
# create a modified version of `iris`
iris2 <- iris
iris2$Sepal.Length <- 5
iris2$Petal.Width[2] <- 1
iris2$row_names <- rownames(iris) # use the row names as unique row ID
dbBind(update, iris2) # send the updated data
dbClearResult(update) # release the prepared statement
# now read the modified data - you will see the updates did work
data1 <- dbReadTable(con, "iris")
dbDisconnect(con)
Run Code Online (Sandbox Code Playgroud)
只有当你拥有我在上面的例子中创建的主键时,才能使用行名称,这些行名称是每行增加1的唯一编号...
有关odbc我在DBI dbConnect语句中使用的包的更多信息,请参阅:https://github.com/rstats-db/odbc
基于 R Yoda 的答案,我为自己创建了下面的辅助函数。这允许使用数据帧来指定更新条件。
虽然我构建它是为了运行事务更新(即单行),但理论上它可以更新传递条件的多行。但是,这与使用输入数据帧更新多行不同。也许其他人可以在此基础上继续发展...
dbUpdateCustom = function(x, key_cols, con, schema_name, table_name) {
if (nrow(x) != 1) stop("Input dataframe must be exactly 1 row")
if (!all(key_cols %in% colnames(x))) stop("All columns specified in 'key_cols' must be present in 'x'")
# Build the update string --------------------------------------------------
df_key <- dplyr::select(x, one_of(key_cols))
df_upt <- dplyr::select(x, -one_of(key_cols))
set_str <- purrr::map_chr(colnames(df_upt), ~glue::glue_sql('{`.x`} = {x[[.x]]}', .con = con))
set_str <- paste(set_str, collapse = ", ")
where_str <- purrr::map_chr(colnames(df_key), ~glue::glue_sql("{`.x`} = {x[[.x]]}", .con = con))
where_str <- paste(where_str, collapse = " AND ")
update_str <- glue::glue('UPDATE {schema_name}.{table_name} SET {set_str} WHERE {where_str}')
# Execute ------------------------------------------------------------------
query_res <- DBI::dbSendQuery(con, update_str)
DBI::dbClearResult(query_res)
return (invisible(TRUE))
}
Run Code Online (Sandbox Code Playgroud)
在哪里