使用存储在R数据帧中的ID {}选择表

时间:2017-01-09 21:07:19

标签: sql r rodbc

我正在尝试在使用RODBC连接“连接在一起”的多个SQL Teradata表中加载表。我想指定唯一的ID,因此它只会提取数据。当我在查询文本中插入一些ID时,SQL语句当前使用“sqlQuery”R函数。但是,我有更多的ID(例如10,000,100,000)我想要为其提取数据。我只有这些ID存储在我的本地R环境中,所以我不能从SQL表中加入它。我的问题是如何通过使用R环境变量引用这些ID来获取这些ID的数据?

我试图提供一个说明问题的例子。该示例显示了一个工作案例,它只是将10个ID直接“粘贴”到SQL语句中。但是,当它们有更多“ID”(10,000,100,000,等等)时,此选项不起作用。不幸的是我没有Teradata DB的权限,所以我不能通过ID加入。我只有.csv文件,SAS数据集等的ID。此外,我不能像这个例子那样将所有ID放在SQL语句中,因为它对所有这些ID来说太长了。我已经看到其他人如何使用SAS SQL语句来“引用”本地SAS环境中的ID(使用*符号),所以我希望我能在R中做类似的事情。谢谢。

#for loading data
library(RODBC)

# Connect to Teradata SQL server
TeradataConnect <- odbcConnect(dsn="****")

#random sample of 10 IDs but their are  many more (e.g., 100,000's)
IDs = c(855820852, 1461838083,  861608839, 1498698119,  817883914,    776309362,
        799069685,  825438654,  856801569, 1749317792)

# specificy dates you want to pull data over
LowDate = Sys.Date() - 365
UpDate = Sys.Date()

#SQL query for pulling data 
SQL_query =  paste("SELECT  Distinct S.ID  
               ,S.LOC_ID
               ,S.DATE
               ,I.ITEM_DESC

               FROM  table.DATA   S
               INNER JOIN item.DATA I
               ON  S.ID=I.ID 

               WHERE  1 =1
               AND I.ITEM_TYPE= 'NORMAL'
               AND S.DATE BETWEEN ", paste(paste0("'", LowDate, "'")), " AND ", paste(paste0("'", UpDate, "'")), "
               AND S.ID IN (", paste(paste(IDs, collapse = ", ")), ") 
               GROUP BY 
               S.ID
               ,S.LOC_ID
               ,S.DATE
               ,I.ITEM_DESC
               ")

#pulls all data from a random sample of IDs
Dataset = sqlQuery(TeradataConnect, SQL_query)

更新:感谢@RYoda的建议。我正在添加SAS代码的示例,以便您可以看到它是如何工作的。我不是SAS专家,但我收到了某些人的询问。我的理解是,他们随时使用“&amp;”在SQL语句中,它将使用SAS环境中的数据的字符(例如,“ids。”,其中id是SAS环境中的变量)。不幸的是我没有对SQL表的写访问权限,所以我不能让数据库完成工作。看起来像是使用了你建议的解决方法,因为预过滤的数据对我来说太大了,无法在我的R环境中加载,然后使用data.table或dplyr join执行连接。我希望我能找到一个更优雅的解决方案,因为他们很多时候我都试图使用像这样的R环境变量来加载/过滤SQL表数据。我认为预期的最终过滤数据大小将是数百万行和~10列。再次感谢你的帮助。

PROC SQL;
 CONNECT TO teradata(db=VIEWS user=&td_user. password=&td_pwd. tdpid=tableid mode=teradata);
 CREATE TABLE Str_inv AS
 SELECT * FROM connection to Teradata
                ( 
                SELECT 
                    nbr1,
                    nbr2,
                    b.item_nbr,
                    sum(inv.qty) AS QTY
                FROM 
                    table.inventory inv
                INNER JOIN
                    table.hier b
                ON
                    inv.item_id=b.item_id
                INNER JOIN 
                    table.loc c
                ON
                    inv.str_loc_id = c.loc_id
                WHERE 
                    inv.cal_dt = &fw_end_dt. AND
                    b.ITEM_TYP_DESC IN ('NORMAL') AND
                    b.CORE_ID = 1 AND
                    b.item_id IN (&ids.)
                GROUP BY
                    1,2,3
                );
QUIT;

0 个答案:

没有答案