【问题标题】:Best way to add a column to data.table by reading data from a variable url通过从变量 url 读取数据将列添加到 data.table 的最佳方法
【发布时间】:2021-04-21 21:55:10
【问题描述】:

我有一个 .csv 文件,其中包含与比特币钱包相关的近 100 万笔交易的交易 ID(发送和接收交易),我将其作为数据表读入 R。现在我正在尝试在表格中添加另一列,其中列出了每笔交易的费用。这可以使用 API 调用来完成。

例如,要获得 txid 73336c8b2f8bbf9c4165de515765463d6e835a9f3f87bf822d8bcb23c074ae7f 的费用,我必须打开: https://blockchain.info/q/txfee/73336c8b2f8bbf9c4165de515765463d6e835a9f3f87bf822d8bcb23c074ae7f 并直接读取那里的数据。

我做了什么:首先我使用 Excel 编辑了 .csv 文件,为每一行的 url 添加一个新列。然后用R写了如下代码:

for(i in 1:nrow(transactions))
transactions$fee[i] <- scan(transactions$url[i])

但这种方式在 1 秒内只更新 2-3 行。由于我是新手,因此必须有更有效的方法来做同样的事情。

【问题讨论】:

  • 如果 API 真的一次只返回一个值,那么您可能基本上已经达到了极限。我看到使用 httr::GET 而不是 scan: type.convert(httr::content(httr::GET(URL))) 有一点加速,但下载步骤将是你最大的瓶颈。唯一的另一件事是并行读取,或者找出 API 是否有办法一次为多个事务生成值。
  • @MichaelChirico 真的。无论采用何种方法从网页中读取数据,对于大量行所花费的时间都是相同的。瓶颈当然在于下载数据。不幸的是,我找不到让 API 一次返回多笔交易费用的方法。我接下来尝试的是手动运行多个 RStudio 实例,并为每个实例中的不同行集收取费用。这给了我大约 4 倍的结果。我想知道是否有更好的并行化方法。

标签: r data.table blockchain.info-api


【解决方案1】:

通过使用curl::curl_fetch_memory,我们可以比scan() 做得更好(~15 倍),例如使用您的网址:

URL <- "https://blockchain.info/q/txfee/73336c8b2f8bbf9c4165de515765463d6e835a9f3f87bf822d8bcb23c074ae7f"

microbenchmark::microbenchmark(
  times = 50L,
  scan = scan(URL, what = integer(), quiet = TRUE),
  GET = as.integer(httr::content(httr::GET(URL))),
  curl = as.integer(rawToChar(curl::curl_fetch_memory(URL)$content))
)
# Unit: microseconds
#  expr      min       lq       mean    median        uq       max neval
#  scan 9388.292 9885.680 10216.9262 10164.120 10502.839 11016.553    50
#   GET 7195.900 7611.485  8342.2855  7832.446  7948.521 22781.104    50
#  curl  511.834  565.067   611.4956   610.391   642.799   790.482    50

identical(
  scan(URL, what = integer(), quiet = TRUE),
  as.integer(rawToChar(curl::curl_fetch_memory(URL)$content))
)
# [1] TRUE

注意:我使用 integer 是因为您的特定 URL 适合,但 as.numeric 可能更合适。

也就是说,我仍然认为访问网络是最大的瓶颈,您可能会发现尝试一次获得 >1 次交易的有效负载会有所收获。否则,您最大的性能提升将来自并行化。

【讨论】:

  • 你说得对,最大的瓶颈确实是访问网页。我为 100 行运行了您建议的所有 3 种方法,无论哪种方法,每种情况下的平均时间都是相同的。在 40 秒内完成大约 100 笔交易。我接下来尝试的是手动运行多个 RStudio 实例,并为每个实例中的不同行集收取费用。这使我能够在 10 秒内处理 100 笔交易。
猜你喜欢
  • 2018-11-09
  • 1970-01-01
  • 1970-01-01
  • 2016-04-26
  • 1970-01-01
  • 2015-01-09
  • 2011-09-08
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多