美文网首页TCGA数据挖掘学R让人秃TCGA
从TCGA数据库下载并整合清洗高通量肿瘤表达谱-临床性状数据

从TCGA数据库下载并整合清洗高通量肿瘤表达谱-临床性状数据

作者: ZZZZZZ_XX | 来源:发表于2020-03-08 18:25 被阅读0次

    TCGA是The Cancer Genome Atlas的简称,由美国NIH管理,是目前出现频率最高,最权威的肿瘤公共数据库。其中收录了人体多个部位肿瘤的高通量测序/基因芯片mRNA、miRNA表达谱数据、基因组变异、甲基化等数据,以及相应样本的人口学特征及临床数据(包括暴露情况、预后、肿瘤分期、治疗手段)。为肿瘤研究的数据挖掘和课题前期分析提供了丰富的资源。

    目前课题非常常见的手(tao)段(lu)就是使用公共数据库挖掘肿瘤高通量转录组数据,发现对抑癌/促癌具有潜在价值的基因或基因模块,随后结合功能实验进行验证和深入机制的探讨。所以对没有条件自己送临床样本/动物实验测序的人来说,TCGA是妥妥的宝藏~

    就从TCGA RNA-seq表达谱数据下载开始吧。写下这个备忘录,以免以后又出现代码不用就忘记的尴尬。

    TCGA官方网站为:https://portal.gdc.cancer.gov

    1.点击Repository框。


    TCGA官网长这样~
    1. 接下来就进入数据类型选择的页面。

    选择下载转录组二代测序数据(芯片已经基本成为过去式了),在左侧的File中需要选择Data Category > Transcriptome Profiling, Data Type > Gene Expression Quantification, Experimental Strategy > RNA-seq.

    Workflow type >: 关于检测gene expression的RNA-seq的数据类型,TCGA提供已经将reads比对好并注释后的Counts (未经标准化的aligned reads数), FPKM(已标准化fragments per kilobase per million), FPKM-UQ(FPKM-upper quartile)下载。

    如何选择:(1)如果需要做差异表达分析,则需下载HTSeq-Counts,数据整合后使用R的EdgeR或DESeq2包分析,它们均需输入未经标准化的原始counts matrix。(2)如需做WGCNA模组分析,推荐下载HTSeq-Counts,经DESeq2包标准化后输入分析。(3)如需做CIBERSORT数字免疫细胞分析,需下载HTSeq-FPKM作为输入数据。(4)...

    这里以FPKM数据下载为例,但Counts数据的流程也完全一样!


    File选项一览
    1. 选择需要分析的Case即肿瘤类型和临床样本特征。

    将左上角的File调到Case,出现Primary site, Program, Gender, Age等信息需要勾选。需根据课题需要进行相关人口学特征的勾选。

    注:为避免后续数据处理中ID转换麻烦,Program需选择TCGA(具有统一的ID特征,可批量处理),project和disease type根据需要的疾病类型勾选。如需做生存分析,Vital status不要勾选某一特定生存状态。

    本次以TCGA项目中特定人种 (white) 的肺鳞癌 (LUSC, Lung squamous cell carcinoma) 为例。勾选条件如下:


    Case选项一览
    1. 添加数据到购物车(Cart)。

    此时样本类型和特征都已经选好。点击页面中上的Add all files to cart,然后点击右上角Cart进入购物车下载。Cart上显示已经纳入了392个样本等待下载。


    购物车安排上
    1. 下载样本的测序数据,临床数据和样本ID信息。

    点击Download > Manifest,该文件随后将作为下载器的输入信息文件下载测序数据。(不推荐通过下载Cart直接获取测序数据,因为数据库网络速度慢,遇到断网或无响应就不能断点续传了)。然后同时需点击下载Metadata以及Clinical > json。


    从网站下载数据文件

    注:第一次使用TCGA,需要点击下载右上角的GDC Data Transfer Tool,根据自己的平台系统选择合适的zip包下载。解压后放入用于储存TCGA下载数据的新建文件夹中。


    gdc下载器的下载页面 此时文件夹中的文件已经准备好了!

    6.测序FPKM表达矩阵下载。

    注:本例使用苹果macbook OS系统操作。我没有windows电脑,所以windows的操作我搜一搜,再补上!

    打开terminal终端,把目录转换到储存上述文件所在的文件夹(根据自己的文件夹路径进行更改),并以下载的manifest文件作为输入,使用gdc编译器下载数据:

    cd /Users/zx/Desktop/TCGA/TCGA-LUSC-white/FPKM/tutorial
    ./gdc-client download -m gdc_manifest_20200308_044238.txt
    

    接下来就是等待...

    Tips:国内最好在白天下载,米国人睡了,传输速度会快一丢丢...但总体来说还是非常感人。而且建议挂学校的学术梯子,有条件挂米国学校的梯子是最好了。

    仅作参考,392个样本,国内下午,我用国内普通网络下载了3个小时;挂了Yale的梯子下载同一批数据,只用了15分钟。:)))


    terminal数据下载-下载完成展示

    7.数据全部下载完成:

    数据下载完成后terminal报告success. 文件夹中会出现392个名字神似乱码(然而不是)的新文件夹,每个新文件夹中都包含有.FPKM.txt.gz(一种压缩包形式),这是我们需要的表达矩阵。我们随后使用R将每个单样本的FPKM表达矩阵进行提取,整合,并与临床数据进行匹配。


    下载完成后的文件夹及所需文件

    接下来的部分使用Rstudio完成:

    需要R包:dplyr, R.utils, tidyr, jsonlite, rtracklayer,第一次使用需要先使用install.packages()下载安装。

    install.packages('dplyr')
    install.packages('R.utils')
    install.packages('tidyr')
    install.packages('jsonlite')
    #rtracklayer is based on bioconductor, so we need to change the way of installation.
    source("https://bioconductor.org/biocLite.R")
    biocLite("rtracklayer")
    
    1. 设置自定义工作路径,加载数据,解压,并将解压后.txt表达矩阵统一放入新文件夹:

    TIPS:gunzip函数是会默认删除压缩包文件,仅保留解压文件的。数据文件下载非常不容易,所以衷心建议各位在批量解压前先整体备份一盘...如果因为匹配pattern或者各种问题导致代码没有循环完成,操作就比较麻烦了!建议找出问题后直接用备份文件重来即可~

    library('R.utils')
    setwd('/Users/zx/Desktop/TCGA/TCGA-LUSC-white/FPKM/tutorial')
    #to make sure this directory will be in the first place when performing the for loop.
    dir.create('00000_extracted_FPKM')
    #The char length of the name of each downloaded expr matrix directory is 36, which is different from other files downloaded from the TCGA website.
    dir_FPKM <- dir()[nchar(dir()) == 36]
    #decompress the separate files and integrate them into a expression matrix.
    for (data in dir_FPKM) {
      filename <- list.files(data, pattern = ".*FPKM")
      R.utils::gunzip(paste0(data,"/",filename))
      file_extracted <- list.files(data, pattern = ".*FPKM.txt$")
      file.copy(paste0(data,"/",file_extracted),"00000_extracted_FPKM")
    }
    
    1. 根据每个单独表达矩阵文件的gene_id,将所有样本合并为一个总表达矩阵。

    每个样本的FPKM.txt由两列组成,第一列为各基因的ENSEMBL GENE ID,第二列为FPKM表达值,不含标题行。

    library('dplyr')
    setwd('/Users/zx/Desktop/TCGA/TCGA-LUSC-white/FPKM/tutorial/00000_extracted_FPKM')
    file_extracted_FPKM <- list.files()
    first_file <- read.table(file_extracted_FPKM[1], header = F, sep = '\t', stringsAsFactors = F)
    names(first_file) <- c('gene_id', substr(file_extracted_FPKM[1], 1, nchar(file_extracted_FPKM[1])-9))
    for (extracted_FPKM in file_extracted_FPKM[2:length(file_extracted_FPKM)]) {
      file_appended <- read.table(extracted_FPKM, header = F, sep = '\t', stringsAsFactors = F)
      names(file_appended) <- c('gene_id', substr(extracted_FPKM, 1, nchar(file_extracted_FPKM[1])-9))  #delete the suffix .FPKM.txt which is made of 9 chars and just maintain the original file names of each sample for following ID conversion.
      first_file <- dplyr::inner_join(first_file, file_appended, by='gene_id')
    }
    expr_FPKM <- first_file
    
    1. 暂停点:此时已获得最原始的总体FPKM表达矩阵,第一列为各基因的ENSEMBL GENE ID,第一行为样本名称(为txt文件中的file_names),可将其输出备用:
    #for original data backup:
    setwd('/Users/zx/Desktop/TCGA/TCGA-LUSC-white/FPKM/tutorial/00000_extracted_FPKM')
    write.csv(expr_FPKM, 'expr_FPKM.csv', quote = F, row.names = F)
    

    若需将原始表达矩阵重新载入:

    注:由于由36个字符组成的file_names很多以数字开头,而R不允许这样的命名方式,所以载入后部分样本名称前会自动加一个字符X。所以需要去除。这里合并操作:

    #to load the expr_FKPM data exported before and remove the char 'X' automatically added in front of colnames starting with number:
    setwd('/Users/zx/Desktop/TCGA/TCGA-LUSC-white/FPKM/tutorial/00000_extracted_FPKM')
    expr_FPKM <- read.csv('expr_FPKM.csv', header = T, stringsAsFactors = F)
    for_replacement_indices <- grep(names(expr_FPKM), pattern = '^X')
    names(expr_FPKM)[for_replacement_indices] <- substr(names(expr_FPKM)[for_replacement_indices], 2, 37)
    
    1. 从网站下载的metadata文件中获得各样本的TCGA_IDs,并将合并表达矩阵的样本名转换为完整的TCGA ID (eg: TCGA-33-4538-01A-01R-1201-07)。
    #get the TCGA IDs of each sample.
    library('jsonlite')
    setwd('/Users/zx/Desktop/TCGA/TCGA-LUSC-white/FPKM/tutorial')
    metadata <- jsonlite::fromJSON(txt = "metadata.cart.2020-03-08.json")
    metadata_id <- dplyr::select(.data = metadata, c(file_name, associated_entities))
    file_name <- c()
    TCGA_ID <- c()
    sub_TCGA_ID_func <- function(x){
      x$entity_submitter_id
    }
    ID_conversion_table <- data.frame('file_names'=substr(metadata_id$file_name, 1, 36), 
                                      'TCGA_IDs'=as.character(lapply(metadata_id$associated_entities, FUN = sub_TCGA_ID_func)), 
                                      stringsAsFactors = F)
    rownames(ID_conversion_table) <- ID_conversion_table$file_names
    colnames(expr_FPKM) <- append('gene_id', ID_conversion_table[colnames(expr_FPKM)[2:length(expr_FPKM)],'TCGA_IDs'])
    
    1. 进一步处理表达矩阵,将第一列的ENSEMBL GENE ID (eg. ENSG00000273842.1)转化为HUGO GENE SYMBOL (eg. DVL1),便于认识和处理。并去除表达矩阵中可能存在的重复基因。最终生成的表达矩阵前三列为Gene symbol, gene id和bio_type.

    TIPS:ENSEMBL数据库下载注释GTF文件速度真的很一言难尽。作为参考,挂了Yale的梯子,45mb左右的文件下载了2个小时。建议不要着急,要微笑:)))

    注:ENSEMBL ID与GENE SYMBOL转换时不含其中的小数点和之后的数字,因此需要将其先去除后再使用GTF注释文件转换。

    library('tidyr')
    library('rtracklayer')
    #trim the gene ID by decimals and translate them into gene symbols
    expr_FPKM <- tidyr::separate(expr_FPKM, gene_id, into = c('gene_id', 'junk'), sep='\\.')
    expr_FPKM <- expr_FPKM[,-2]
    #download the annotation file containing ENS IDs, gene symbols, and biotypes.
    download.file('ftp://ftp.ensembl.org/pub/release-99/gtf/homo_sapiens/Homo_sapiens.GRCh38.99.chr.gtf.gz',
                  'Homo_sapiens.GRCh38.99.chr.gtf.gz')
    R.utils::gunzip('Homo_sapiens.GRCh38.99.chr.gtf.gz')
    gtf1 <- rtracklayer::import('Homo_sapiens.GRCh38.99.chr.gtf')
    gtf_df <- as.data.frame(gtf1)
    #Only select the protein coding genes.
    mRNA_exprSet <- gtf_df %>%
      dplyr::filter(type=="gene",gene_biotype=="protein_coding") %>%
      dplyr::select(c(gene_name,gene_id,gene_biotype)) %>%
      dplyr::inner_join(expr_FPKM,by ="gene_id")
    mRNA_exprSet <- mRNA_exprSet[!duplicated(mRNA_exprSet$gene_name),]
    
    1. 载入临床特征数据,并进行其中缺失数据的清洗。本例中需要保存的临床数据包括病人的性别(gender),肿瘤分期(tumor stage),生存时间(overall survival),以及生存状态(原vital status,数据清洗后改为censoring status)。

    TIPS:之前下载的392个数据中既包含所有病人的癌组织也包含部分病人的癌旁组织,因此文件数量多于实际病人数。此时获得的临床特征数据以病人为单位(n=349),小于下载总样本数,等于总样本中癌症样本数。

    注:overall survival的计算方法:临床数据中包含days_to_death以及days_to_last_follow_up两行数据,仅vital status为Dead的样本会有days_to_death数据,而Alive的样本记录有days_to_last_follow_up,以及有极少数样本两项数据均缺失。因此在overall_survival中,死亡样本以days_to_death为结局发生天数,而存活样本以days_to_last_follow_up作为删失发生天数。overall_survival与censoring_status配合,在生存分析中会用到。

    clinical_data_original <- jsonlite::fromJSON('clinical.cart.2020-03-08.json')
    filter_follow_up <- function(x){
      x$days_to_last_follow_up
    }
    filter_tumor_stage <- function(x){
      x$tumor_stage
    }
    days_to_last_follow_up <- as.numeric(lapply(clinical_data_original$diagnoses, filter_follow_up))
    tumor_stage <- as.character(lapply(clinical_data_original$diagnoses, filter_tumor_stage))
    clinical_trait <- clinical_data_original$demographic[,c('submitter_id', 'gender', 'days_to_death', 'vital_status')] %>%
      cbind(days_to_last_follow_up, tumor_stage)
    clinical_trait$tumor_stage <- as.character(clinical_trait$tumor_stage)
    clinical_trait <- tidyr::separate(clinical_trait, col= 'submitter_id',
                                      into = c('submitter_id', 'junk'), sep='_', remove = T)[,-2]
    clinical_trait <- clinical_trait[!duplicated(clinical_trait$submitter_id),]
    clinical_trait[is.na(clinical_trait$days_to_death), 'days_to_death'] <- clinical_trait[is.na(clinical_trait$days_to_death), 'days_to_last_follow_up']
    clinical_trait <- clinical_trait[,-5]
    names(clinical_trait) <- c('submitter_id', 'gender', 'overall_survival', 'censoring_status', 'tumor_stage')
    clinical_trait <- clinical_trait %>% dplyr::filter(!(is.na(overall_survival))) %>% dplyr::filter(tumor_stage != 'not reported')
    
    1. 通过TCGA_ID将所有样品分组。

    思路是:TCGA ID由dash隔开,第四个模块记录了样本的分组。若该模块中编号为01-09则为肿瘤,若编号在10-29则为正常癌旁样本。

    #classify the samples by TCGA_IDs (TCGA-XX-XXXX-NN: NN < 10 are cancer samples, otherwise are normal samples).
    condition_table <- tidyr::separate(data=data.frame('ids'=colnames(expr_FPKM)[2:length(expr_FPKM)]),
                                      col='ids',
                                      sep='-',
                                      into=c('c1','c2','c3','c4','c5','c6','c7'))
    condition_table <- cbind('ids'=colnames(expr_FPKM)[2:length(expr_FPKM)], condition_table) %>%
      cbind('submitter_IDs'=substr(colnames(expr_FPKM)[2:length(expr_FPKM)], 1, 12))
    condition_table$c4 <- gsub(condition_table$c4, pattern = '^0..', replacement = 'cancer')
    condition_table$c4 <- gsub(condition_table$c4, pattern = '^1..', replacement = 'normal')
    condition_table <- condition_table[,c('ids','c4','submitter_IDs')]
    names(condition_table) <- c('TCGA_IDs', 'sample_type', 'submitter_id')
    condition_table$submitter_id <- as.character(condition_table$submitter_id)
    condition_table$TCGA_IDs <- as.character(condition_table$TCGA_IDs)
    
    1. 去除表达矩阵中肿瘤或正常组内可能存在的重复样本,并将cancer样本与临床数据匹配。

    由于一个样本可能测序多次,所以可以通过submitter_ID (也就是TCGA_ID的前12位)将组内重复去除。我这里采取的办法是保留第一次在表达矩阵中出现的样本,去除随后出现的重复样本。此外由于此前有部分病人存在信息缺失,已被剔除,现也只保留含有全部信息的病人cancer样本。(normal样本不需匹配临床信息,因为仅用于差异表达分析,不会涉及后续生存分析或WCGNA分析)

    注:由于normal组的癌旁组织也来源于病人,所以需要组内分开去除重复,否则来源于统一病人的normal和cancer样本会被去除其一。

    #remove the duplicated samples within groups and only maintain the cancer samples with clinical data.
    condition_table_cancer <- condition_table[condition_table$sample_type=='cancer',]
    condition_table_cancer <- condition_table_cancer[!duplicated(condition_table_cancer$submitter_id),] %>%
      dplyr::inner_join(clinical_trait, by='submitter_id')
    condition_table_normal <- condition_table[condition_table$sample_type=='normal',]
    condition_table_normal <- condition_table_normal[!duplicated(condition_table_normal$submitter_id),]
    condition_table <- rbind(condition_table_cancer[1:3], condition_table_normal)
    
    1. 获得最终可以进行下游分析的规范FPKM表达矩阵。

    该矩阵第一列为GENE SYMBOL,第一行为样本TCGA_ID,其余为FPKM表达数据。

    #get the final total FPKM expr matrix and expr matrix containing cancer samples for downstream cibersort analyses.
    mRNA_exprSet_cancer_only <- mRNA_exprSet[,c('gene_name', condition_table_cancer$TCGA_IDs)]
    mRNA_exprSet <- mRNA_exprSet[,c('gene_name', condition_table$TCGA_IDs)]
    write.csv(mRNA_exprSet, '/Users/zx/Desktop/TCGA/TCGA-LUSC-white/FPKM/tutorial/FPKM_matrix_LUSC_.csv', quote = F, row.names = F)
    

    到此为止TCGA表达矩阵的数据下载和清洗整合就全部结束了!!!

    开不开心!!!(不)

    最后输出的表达矩阵就是长这样的:


    FPKM矩阵在excel中的部分展示

    说在最后:关于counts数据的下载...

    几乎一模一样,镜像操作即可!唯一的区别是在初始表达矩阵整合完成后,需要去除dataframe的最后5行,该5行是样本的总结性数据,在后续分析中不会用到,直接去除即可。


    某样本中Counts表达矩阵需要删除的部分

    相关文章

      网友评论

        本文标题:从TCGA数据库下载并整合清洗高通量肿瘤表达谱-临床性状数据

        本文链接:https://www.haomeiwen.com/subject/jcrjdhtx.html