2

我有一个包含 x、y 和 z 列的 sqlite 表。x 和 y 是唯一键,z 是值。

我想使用 R 将数据插入到这个表中。如果正在插入基于 x 和 y 字段的重复记录,我希望 sqlite 拒绝该记录并继续。在sql中,这可以使用“插入或忽略”来完成,这可以使用R包RSQLite来完成吗?到目前为止,有一个选项 dbWriteTable 将 R 数据帧写入 sqlite 表,但似乎没有“插入或忽略”选项

4

4 回答 4

3

我找到了 dbWriteTable 构造 sql 字符串并将其发送到 sqlite 的源。您可以使用此修改后的源来允许“插入或忽略”语法

https://gist.github.com/jeffwong/5925000

于 2013-07-04T17:17:44.750 回答
2

对@Karsten W 的回答进行了返工,以使用相同的流程加载所有数据:

library(RSQLite)

# create table
con <- dbConnect(drv=RSQLite::SQLite(), ":memory:")
dbExecute(con, "CREATE TABLE tab1 (a CHAR(6) NOT NULL, b CHAR(6) NOT NULL, PRIMARY KEY (a, b));")

load_data <- function(x) {
    # load data
    # we want to add only the new combinations of a and b
    insertnew <- dbSendQuery(con, "INSERT OR IGNORE INTO tab1 VALUES (:a,:b)")
    dbBind(insertnew, params=x)  # execute
    dbClearResult(insertnew)     # release the prepared statement
}


# new data
dat1 <- data.frame(a=letters[1:10], b=LETTERS[11:20], stringsAsFactors=FALSE)
load_data(dat1)
print(dbGetQuery(con, "SELECT COUNT(*) FROM tab1;"))

# new data, partly redundant
dat1 <- data.frame(a=letters[2:11], b=LETTERS[12:21], stringsAsFactors=FALSE)
load_data(dat1)
print(dbGetQuery(con, "SELECT COUNT(*) FROM tab1;"))
于 2018-08-19T21:38:32.080 回答
1
results <- dbSendQuery(exampledb, "insert or ignore ...") 

根据DBI 规范,dbSendQuery 采用原始 SQL 。希望有帮助...

于 2013-07-04T05:31:15.000 回答
1

由于我有类似的问题,这里是一个单一的解决方案:

library(RSQLite)

# create table
con <- dbConnect(drv=RSQLite::SQLite(), ":memory:")
dbExecute(con, "CREATE TABLE tab1 (a CHAR(6) NOT NULL, b CHAR(6) NOT NULL, PRIMARY KEY (a, b));")
dat1 <- data.frame(a=letters[1:10], b=LETTERS[11:20], stringsAsFactors=FALSE)
dbWriteTable(con, "tab1", dat1, append=TRUE)

# new data, partly redundant
dat2 <- data.frame(a=letters[2:11], b=LETTERS[12:21], stringsAsFactors=FALSE)

# we want to add only the new combinations of a and b
insertnew <- dbSendQuery(con, "INSERT OR IGNORE INTO tab1 VALUES (:a,:b)")
dbBind(insertnew, params=dat2) # execute
dbClearResult(insertnew)  # release the prepared statement

# should be TRUE
as.numeric(dbGetQuery(con, "SELECT COUNT(*) FROM tab1;"))==11
于 2018-01-31T15:01:27.103 回答