Re: [問題] 以時間間隔為條件,抽取資料
感謝原原po的發問以及c大的解答
正好也遇到類似的狀況
但照著做之後,
# 計算時間差,以小時表示
DT[ , diffTime := difftime(time, time[min(k, .N)], units="hours"), by = ind]
這一段都會跳出error......
Error in `[.data.frame`(DT, , `:=`(diffTime, difftime(time, time[min(k, :
unused argument (by = ind)
我是將自身資料擷取出來, 欄位名全都改成跟c大的資料一樣
用c大產生的資料下去跑沒問題
但內容換成我的資料就會錯誤
我的資料格式如下:
ind是"character", time是"POSIXct" "POSIXt",
照理應該是符合規則, 不知卡在哪?
然後我要保留的條件與原文也有所不同
以原文為例:
個體A 2012/10/11 20:00 實驗資料OOXX
個體A 2012/10/11 23:00 實驗資料OOXX
個體A 2012/10/12 03:00 實驗資料OOXX
個體B 2012/12/11 05:00 實驗資料OOXX
個體B 2012/12/11 11:05 實驗資料OOXX
個體B 2012/12/11 13:00 實驗資料OOXX
個體B 2012/12/11 18:00 實驗資料OOXX
個體B 2012/12/11 20:00 實驗資料OOXX
A個體保留第一、第三筆資料
B個體保留第一、第二、第四筆資料
我則是要保留相近時間內(與上一筆擷取的時間不超過6小時)的最後一筆
其結果會是: A個體保留第3筆, B個體保留第1、5筆
對於B個體而言
05:00
|----> 間隔大於6小時, 則保留5:00, 下一筆開始為新的區間
11:05
13:00 這幾筆彼此與前一筆間隔未超過6小時, 則視為同個區間
18:00 取最後一筆20:00
20:00
這樣又該如何調整程式呢??
不知是否有人可以提供建議呢? 非常感謝!
※ 引述《celestialgod (天)》之銘言:
: ※ 引述《anakinyen (我在台北 天氣晴)》之銘言:
: : [問題類型]:
: : 程式諮詢(我想用R 做某件事情,但是我不知道要怎麼用R 寫出來)
: : [軟體熟悉度]:
: : 新手,只會套用package
: : [問題敘述]:
: : 我有一批動物研究的資料
: : 資料大致長這個樣子,共有12隻個體一萬多筆
: : 個體A 2012/10/11 20:00 實驗資料OOXX
: : 個體A 2012/10/11 23:00 實驗資料OOXX
: : 個體A 2012/10/12 03:00 實驗資料OOXX
: : 個體B 2012/12/11 05:00 實驗資料OOXX
: : 個體B 2012/12/11 11:05 實驗資料OOXX
: : 個體B 2012/12/11 13:00 實驗資料OOXX
: : 個體B 2012/12/11 18:00 實驗資料OOXX
: : 個體B 2012/12/11 20:00 實驗資料OOXX
: : 由於時間間隔過短的話,資料之間可能有相關性
: : 因此我現在想要設定6小時的閥值,間隔超過6小時的資料才會保留
: : 以上面資料為例
: : A個體保留第一、第三筆資料
: : B個體保留第一、第二、第四筆資料
: : 我的程度是新手,偶爾會拿一些package來套用
: : 請教是否有相關套件或現成code可以用在這個案例
: : 非常感謝~~
: 我用while + data.table做,若用data.frame會複製很多次,效率會不彰
: library(data.table)
: # 產生資料
: numObs <- 50
: numInd <- 5
: DT <- data.table(ind = paste0("A", sample(numInd, numObs, TRUE)),
: time = strptime("2012/12/11", "%Y/%m/%d") +
: sample(86400, numObs, TRUE),
: obs = rnorm(numObs))
: # 排序
: setorder(DT, ind, time, obs)
: # 移除掉時間差小於六小時的
: k <- 1
: while ( TRUE ) {
: # 計算時間差,以小時表示
: DT[ , diffTime := difftime(time, time[min(k, .N)], units="hours"), by = ind]
: # 留下自己那一組
: set(DT, which(DT$diffTime == 0), which(names(DT) == "diffTime"), 1e6)
: # 留下時間差超過六小時的
: DT <- DT[abs(diffTime) > 6, ]
: # 下一組
: k <- k + 1
: # 如果k大於全部組的最大觀測值數目就跳離迴圈
: if (k > max(DT[ , .(numObsGroup = .N), by = ind]$numObsGroup))
: break
: }
: # 移除diffTime這個變數
: DT[ , diffTime := NULL]
: 五萬筆觀測值,一千個個體,耗時0.23秒 (平均一個個體50個觀測值)
: 五十萬筆觀測值,一千個個體,耗時0.39秒 (平均一個個體500個觀測值)
: 我覺得這個速度應該可以接受
: 不過我的區間只有24小時,所以可能都很快就篩選完了
: 有人可以試試看更長時間的表現
: 有問題或任何人有更好解法,歡迎提供,感謝
: Note: 間隔一百天,五十萬筆觀測值,一千個個體,耗時18.33秒
--
※ 發信站: 批踢踢實業坊(ptt.cc), 來自: 36.234.37.26 (臺灣)
※ 文章網址: https://www.ptt.cc/bbs/R_Language/M.1569535893.A.084.html
※ 編輯: beatnik (36.234.37.26 臺灣), 09/27/2019 06:12:17
→
09/27 10:10,
5年前
, 1F
09/27 10:10, 1F
沒錯, 我後來有發現我耍笨了....= ="
謝謝指正!
→
09/27 10:20,
5年前
, 2F
09/27 10:20, 2F
→
09/27 10:22,
5年前
, 3F
09/27 10:22, 3F
只要彼此之間不間隔超過所設定之時間(如:6小時)
則都算同一時間區間
A的話, 每一筆都與前一筆不超過6小時
所以取它們的最後一筆--第3筆
這邊用6小時舉例可能比較難想像
若是以間隔不超過10分鐘為條件, 則取連續觀測中的最後一筆
如:
13:01
13:05
13:11 v 取這筆(前3筆彼此都不間隔超過10分鐘)
14:22 --> 與前筆差10分鐘以上, 故視為新一批不同於前面的觀測值
14:25 v 取這筆
為何要取最後一筆?
是因為在本案之間隔10分鐘內的數值, 可能不具參考性
中間會一直重複測量直到正確為止
所以最後一筆才是我想要的修正後或正確的數值
10分鐘以上再出現的數值, 表示又開始測量另一個批次
在短時間內(10分鐘內)量很多次後, 一樣只抓最後一筆
抱歉有點複雜@@
※ 編輯: beatnik (36.234.37.26 臺灣), 09/27/2019 10:52:07
→
09/27 15:52,
5年前
, 4F
09/27 15:52, 4F
→
09/27 19:05,
5年前
, 5F
09/27 19:05, 5F
→
09/28 02:18,
5年前
, 6F
09/28 02:18, 6F
→
09/28 02:41,
5年前
, 7F
09/28 02:41, 7F
→
09/28 02:43,
5年前
, 8F
09/28 02:43, 8F
→
09/28 02:58,
5年前
, 9F
09/28 02:58, 9F
→
09/28 03:02,
5年前
, 10F
09/28 03:02, 10F
→
09/29 06:53,
5年前
, 11F
09/29 06:53, 11F
討論串 (同標題文章)
本文引述了以下文章的的內容:
完整討論串 (本文為第 8 之 8 篇):
R_Language 近期熱門文章
PTT數位生活區 即時熱門文章