非度量多维标度(NMDS)分析
非度量多维标度(Non-metric Multidimensional Scaling,NMDS)是一种将多维空间的研究对象(样本或变量)简化到低维空间进行定位、分析和归类,同时又保留对象间原始关系的数据分析方法。
与PCoA相似,NMDS都使用样本相似性距离矩阵进行降维排序分析,但NMDS侧重反映距离矩阵中数值的排序关系,NMDS图形常用作微生物群落研究的β分析。
来看看R的vegan包和ggplot2包是如何绘制NMDS图的。
使用数据文件如下:
①otu_table.txt
②group.txt
方法如下:
1.调用vegan包metaMDS()函数执行NMDS,读取数据;
library(vegan)
##第 1 种模式,输入距离矩阵排序
#读取 OTU 丰度表
otu <- read.delim("otu_table.txt", row.names = 1, sep = '\t', stringsAsFactors = FALSE, check.names = FALSE)
otu <- data.frame(t(otu))
2.根据物种组成计算样方距离,如 Bray-curtis 距离;
详情 ?vegdist
bray_dis <- vegdist(otu, method = 'bray') #结果以 dist 数据类型存储
3.NMDS 排序,定义 2 个维度;
#NMDS 排序,定义 2 个维度,详情 ?metaMDS
nmds_dis <- metaMDS(bray_dis, k = 2)
4.提取应力函数值、样方得分,查看主要结果;
#应力函数值,一般不大于 0.2 为合理
nmds_dis$stress
#样方得分
nmds_dis_site <- data.frame(nmds_dis$points)
#write.table(nmds_dis_site, 'nmds_dis_site.txt', sep = '\t', col.names = NA, quote = FALSE)
5.物种变量可通过丰度加权平方被动添加至排序图中;
详情 ?wascores
nmds_dis_species <- wascores(nmds_dis$points, otu)
6.使用ggplot2包作图。
library(ggplot2)
#主要展示 top10 丰度物种
abundance <- apply(otu, 2, sum)
abundance_top10 <- names(abundance[order(abundance, decreasing = TRUE)][1:10])
species_top10 <- data.frame(nmds_dis_species[abundance_top10,1:2])
species_top10$name <- rownames(species_top10)
#添加分组信息 上传分组文件
nmds_dis_site$name <- rownames(nmds_dis_site)
map<-read.table("group.txt",header=T,sep="\t",row.names=1)
#nmds_dis_site$group <- map$group
merged=merge(nmds_dis_site,map,by="row.names",all.x=TRUE)
color=c( "#3C5488B2","#00A087B2",
"#F39B7FB2","#91D1C2B2",
"#8491B4B2", "#DC0000B2",
"#7E6148B2","yellow",
"darkolivegreen1", "lightskyblue",
"darkgreen", "deeppink", "khaki2",
"firebrick", "brown1", "darkorange1",
"cyan1", "royalblue4", "darksalmon",
"darkgoldenrod1", "darkseagreen", "darkorchid")
#grid.col[row.names(data)] = color[1:dim(data)[1]]
p <- ggplot(data = merged, aes(MDS1, MDS2)) +
geom_point(size=2,aes(color = group,shape = group)) +
stat_ellipse(aes(fill = group), geom = 'polygon', level = 0.95, alpha = 0.1, show.legend = FALSE) + #添加置信椭圆,注意不是聚类
scale_color_manual(values =color[1:length(unique(map$group))]) +
scale_fill_manual(values = color[1:length(unique(map$group))]) +
theme(panel.grid.major = element_line(color = 'gray', size = 0.2), panel.background = element_rect(color = 'black', fill = 'transparent'),
plot.title = element_text(hjust = 0.5),legend.title = element_blank()) +
#, legend.position = 'none'
geom_vline(xintercept = 0, color = 'gray', size = 0.5) +
geom_hline(yintercept = 0, color = 'gray', size = 0.5)+
geom_text(data = species_top10, aes(label = name), color ="royalblue4", size = 4)+
geom_text(data =merged, aes(label = Row.names,x =MDS1, y = MDS2), size=4, check_overlap = TRUE)
#geom_text(data = species_top10, aes(label = name), color = 'blue', size = textsize)
p