【用戶需求】
有一個大文件,有很多行(lines = 10w?)。只有少數的行滿足用戶關注的條件,記爲cond(line) (返回真表示滿足條件,假表示不滿足)
如果第 i 行滿足條件,則第 i 行的前後 r 行也附加關注,作爲第 i 行的參考(r = 10 ?)
輸出所有的關注行(包括附加關注行)
如果計算了重疊的關注行,僅輸出一次(即下一關注行的前 r 行和前一關注行的後 r 行有重疊,不重複輸出重疊的行)
【算 法】
設定:
KLinesIn 輸入緩衝,KLinesOut 輸出緩衝
ci 當前輸入行 (current line No. i)
pr = [ prb,pre ] 前一個可以輸出的區間 (prev range begin, end)
pcl 前一個滿足 cond(pcl) 的行 (prev cond line = pre - r)
初始化:
ci = 0
prb = 0, pre = -1 (pr = [ 0,-1 ] 爲空區間)
1. 從文件讀取 k 行到 KLinesIn [ 0..k-1 ] 緩衝區 ( k = 1000 )
2. 從 KLinesIn 緩衝區,依次取一行進行分析;設當前行爲 ci (0 <= ci <= k-1 )
2.1 分析 KLinesIn 循環
for KLinesIn [ 0..k-1 ] :
若 cond(ci) 爲真, 則當前可以輸出的區間爲 cr = [ ci-r,ci+r ];將 cr 與 pr = [ prb, pre ] 進行比較;
- 若 cr 和 pr 相交,即 ci-r <= pre,則當前區間可併入前一區間,即 pre = ci + r
若 cond(ci) 爲假
- 不處理
2.2 循環結束,先將 pr 輸出到 KLinesOut (跳過越界部分)
若 pre >= k, prb = 0, pre = pre - k, nk = k (nk表示下次需要讀取的行數)
若 pre < k, prb = 0, pre = -1
- 若 pre >= k-1-r, nk = pre+1
- 若 pre < k-1-r, nk = k-r
ci = 0
2.3 讀取 nk 行,跳到 2.1 繼續執行,知道文件讀取結束
3. 若LinesOut [ 0..k-1 ] 滿,則輸出