1 ライブラリーロード


2 fastqのkmerカウント(リードの長さが同じ場合).


2.2 Biostrings::subseqを用いてリードのpositionごとにkmerカウント.

  • Biostrings::subseqでは全配列の指定positionから部分配列をまとめて取得可能.
  • startをベクトルで与えることができないため, リードの長さが同じでなければk-merの取得ができない.
k-mer contents using Biostrings::subseq
kmer s01 s02 s03 s04 s05
AAAAAAA 13 6 4 4 3
AAAAAAC 8 6 0 0 0
AAAAAAG 6 7 1 1 2
AAAAAAT 9 3 1 0 0
AAAAACA 5 9 4 2 0
AAAAACC 2 6 6 0 0
total k-mer
kmer count
GGGGGGG 1497
CCCCCCC 1409
CAGCAGC 608
GCTGCTG 588
GCAGCAG 540
CTGCTGC 530

3 fastqのk-merカウント(リード毎に長さが異なる場合).


3.2 リード毎にstringr::str_subを用いてk-merカウント.

  • k-merのリストを取得後, NAでfillしてデータフレームに変換後, dplyr, tidyrを使って集計
  • リードの方をNで埋めてBiostrings::subseqを用いた場合, リード数が増えても時間はたいしてかわらなかった.
k-mer content for different read length
kmer s01 s02 s03 s04 s05
AAAAAAA 13 5 3 3 2
AAAAAAC 8 6 0 0 0
AAAAAAG 6 7 1 1 2
AAAAAAT 9 3 1 0 0
AAAAACA 5 9 4 2 0
AAAAACC 2 6 6 0 0
total k-mer
kmer count
CAGCAGC 511
GCTGCTG 501
GCAGCAG 448
CTGCTGC 446
GGAGGAG 443
CAGCAGG 426

4 fastqファイルを分割して並列処理.


4.1 stringr::str_subを使ってリード毎にk-merカウントする関数

  • 入力はfastqファイルパスもしくはDNAStringsetオブジェクト
  • 戻り値の形をresfmtで指定する. リードポジションごとのk-mer数 “pos” もしくは総リードのk-mer数 “total”. それぞれデータフレームで返す.

4.2 リードを分割して並列処理を行う.

  • fastqデータを分割して, 処理する.
    • スレッド毎に均等になるように(リード数で)分割して実行する.
    • foreachを用いて分割したリードの処理を上記の関数を用いておこなった.
    • chunkごとの結果を全部dplyr::bind_rowsしてから集計する.
    • タイプをPSCOKでも実行できるようにしたが, FORKでやるべき.
  • 取りうるk-merセットを作ってからだと行列が巨大になりすぎるのと, 組み合わせをつくるだけで時間がかかりすぎるので~~配列中のk-merのリスト(df)を作って, それにleft_joinすることにした. ~~
  • ~~複数のdfを逐次結合するのにReduceは時間がかかりすぎるのでpurrr::reduceを使ってみたが時間はほぼ変わらない. ~~

  • parallel::clusterExportは, varlistで指定されたマスタープロセス上の変数の値を, ワーカープロセス内の同名の変数に割り当てる. 文字列で与える.
  • parallel::clusterEvalQでも似たようにできる. ワーカープロセス上で関数定義

5 リードボジション毎のkmer出現確率

# positionごとのにkmerカウントデータからkmer出現確率のggplot
gg_kmer <- function(x, h = 10, topn = 10){
  # サンプル毎のkmer出現率の期待値のリスト
  obs_exp <- cbind(kmer = x$kmer, sweep(x[-1], 1, apply(x[-1], 1, mean), "/"))
  obs_exp <- obs_exp %>% 
    mutate(kmer = paste(rownames(obs_exp), kmer, sep = ":")) # 行番号で比較するため
  
  # 出現確率top10のkmer
  obs_exp_top <- obs_exp[order(apply(x[-1], 1, sum), decreasing = T)[1:topn],]
  gg_top <- obs_exp_top %>%
    mutate(kmer = factor(kmer, levels = kmer)) %>%
    tidyr::gather(key = start, value = count, -kmer, factor_key = T) %>%
    ggplot2::ggplot(ggplot2::aes(x = start, y = count, colour = kmer, group = kmer)) +
    ggplot2::theme_bw() +
    ggplot2::theme(axis.text.x = ggplot2::element_text(size = 8, angle = 90, hjust = 1)) +
    ggplot2::labs(title = "top 10 of total positions", y = "Obs/Exp") +
    ggplot2::geom_line()
  
  # 先頭x塩基で出現確率Obs/Expがtopのkmer
  gg_head <- 
    obs_exp[apply(obs_exp[,2:(1 + h)], 2, which.max),] %>%
    tidyr::gather(key = start, value = count, -kmer, factor_key = T) %>%
    ggplot2::ggplot(ggplot2::aes(x = start, y = count, colour = kmer, group = kmer)) +
    ggplot2::theme_bw() +
    ggplot2::theme(axis.text.x = ggplot2::element_text(size = 8, angle = 90, hjust = 1)) +
    ggplot2::labs(title = "top 10 at head 10 nuc", y = "Obs/Exp") +
    ggplot2::geom_line()

  return(list(gg_top, gg_head))
}


# k-mer content
kmer_pos <- kmer_cnt(fa, k = 7, "pos")

# create ggplot object
gg_km <- gg_kmer(x = kmer_pos, h = 10, topn = 10)

do.call(gridExtra::grid.arrange, c(gg_km, list(ncol = 2)))

6 環境

## R version 3.5.1 (2018-07-02)
## Platform: x86_64-apple-darwin15.6.0 (64-bit)
## Running under: macOS High Sierra 10.13.1
## 
## Matrix products: default
## BLAS: /Library/Frameworks/R.framework/Versions/3.5/Resources/lib/libRblas.0.dylib
## LAPACK: /Library/Frameworks/R.framework/Versions/3.5/Resources/lib/libRlapack.dylib
## 
## locale:
## [1] ja_JP.UTF-8/ja_JP.UTF-8/ja_JP.UTF-8/C/ja_JP.UTF-8/ja_JP.UTF-8
## 
## attached base packages:
## [1] stats4    parallel  stats     graphics  grDevices utils     datasets 
## [8] methods   base     
## 
## other attached packages:
##  [1] microbenchmark_1.4-6        gridExtra_2.3              
##  [3] ggplot2_3.1.0               doParallel_1.0.14          
##  [5] iterators_1.0.10            foreach_1.4.4              
##  [7] tibble_2.0.1                tidyr_0.8.2                
##  [9] dplyr_0.8.0.1               stringr_1.3.1              
## [11] ShortRead_1.38.0            GenomicAlignments_1.16.0   
## [13] SummarizedExperiment_1.10.1 DelayedArray_0.6.6         
## [15] matrixStats_0.54.0          Biobase_2.40.0             
## [17] Rsamtools_1.32.3            GenomicRanges_1.32.7       
## [19] GenomeInfoDb_1.16.0         Biostrings_2.48.0          
## [21] XVector_0.20.0              IRanges_2.14.12            
## [23] S4Vectors_0.18.3            BiocParallel_1.14.2        
## [25] BiocGenerics_0.26.0        
## 
## loaded via a namespace (and not attached):
##  [1] Rcpp_1.0.0             lattice_0.20-38        assertthat_0.2.0      
##  [4] digest_0.6.18          R6_2.3.0               plyr_1.8.4            
##  [7] evaluate_0.12          highr_0.7              httr_1.4.0            
## [10] pillar_1.3.1           zlibbioc_1.26.0        rlang_0.3.1           
## [13] lazyeval_0.2.1         rstudioapi_0.9.0       Matrix_1.2-15         
## [16] rmarkdown_1.11         labeling_0.3           webshot_0.5.1         
## [19] readr_1.3.1            RCurl_1.95-4.11        munsell_0.5.0         
## [22] compiler_3.5.1         xfun_0.4               pkgconfig_2.0.2       
## [25] htmltools_0.3.6        tidyselect_0.2.5       GenomeInfoDbData_1.1.0
## [28] codetools_0.2-16       viridisLite_0.3.0      crayon_1.3.4          
## [31] withr_2.1.2            bitops_1.0-6           grid_3.5.1            
## [34] gtable_0.2.0           pacman_0.5.0           magrittr_1.5          
## [37] scales_1.0.0           stringi_1.2.4          hwriter_1.3.2         
## [40] latticeExtra_0.6-28    xml2_1.2.0             kableExtra_1.0.0      
## [43] RColorBrewer_1.1-2     tools_3.5.1            glue_1.3.0            
## [46] purrr_0.3.0            hms_0.4.2              yaml_2.2.0            
## [49] colorspace_1.4-0       rvest_0.3.2            knitr_1.21