降维、特征提取与流形学习--非负矩阵分解(NMF)
非负矩阵分解(NMF)是一种无监督学习算法,目的在于提取有用的特征(可以识别出组合成数据的原始分量),也可以用于降维,通常不用于对数据进行重建或者编码。
- NMF将每个数据点写成一些分量的加权求和(与PCA相同),并且分量和系数都大于0,
- 只能适用于每个特征都是非负的数据(正负号实际上是任意的)。
1、将NMF应用于模拟数据
应用NMF时,我们必须保证数据是正的

如图
两个分量的NMF:分量指向边界,所有的数据点都可以写成这两个分量的正数组合。
一个分量的NMF:分量指向平均值,指向这里可以对数据做出最好的解释。
在NMF中,不存在“第一非负分量”,所有分量地位平等,减少分量个数会删除一些方向。NMF使用了随机初始化,根据随机种子的不同可能会产生不同的结果。
2、将NMF应用于人脸图像
NMF的主要参数(n_components参数):想要提取的分量个数。这个数字通常要小于输入特征的个数(否则将每个像素作为单独的分量就可以解释数据)。
(1)先观察一下运用NMF找到的15个分量长什么样
from sklearn.datasets import fetch_lfw_people
from sklearn.decomposition import PCA
from sklearn.model_selection import train_test_split
import numpy as np
from matplotlib import pyplot as plt
people = fetch_lfw_people(min_faces_per_person=40,resize=0.7)
image_shape = people.images[0].shape
#每个人最多有50张照片,防止数据偏斜
mask = np.zeros(people.target.shape,dtype=bool)
for target in np.unique(people.target):
mask[np.where(people.target==target)[0][:50]]=1
X_people = people.data[mask]
y_people = people.target[mask]
X_train, X_test, y_train, y_test = train_test_split(X_people,y_people,stratify=y_people,random_state=42)
#画出nmf模型训练得到的各个分量(这里指定15个),每个分量都是一张有点人形的图片(因为每个分量保留了所有的原始特征)。
#所有的数据点都可以写成这些分量的加权求和
from sklearn.decomposition import NMF
nmf = NMF(n_components=15,random_state=0)
nmf.fit(X_train)
X_train_nmf = nmf.transform(X_train)
X_test_nmf = nmf.transform(X_test)
fix,axes = plt.subplots(3,5,figsize=(15,12),subplot_kw={'xticks':(),'yticks':()})
for i ,(component,ax) in enumerate(zip(nmf.components_,axes.ravel())):
ax.imshow(component.reshape(image_shape))
ax.set_title("{}.component".format(i))

(2)、按照某个分量,重建数据点
#将数据样本点按照第10个分量排序,绘制数据点中前10张图片
compn = 10
inds = np.argsort(X_train_nmf[:,compn])[::-1] #按照第三个分量排序
fig,axes = plt.subplots(2,5,figsize=(15,8),subplot_kw={'xticks':(),'yticks':()})
for i ,(ind,ax) in enumerate(zip(inds,axes.ravel())):
ax.imshow(X_train[ind].reshape(image_shape))

- 可以看出在所有数据点中,分量10排名前10的数据点长什么样(它们的具有分量10提取的特点,脸有点歪)
- 每个分量提取了数据的不同模式,将这些分量叠加(加权求和)就能重构出训练集中的每一张图像。
3、应用于具有叠加结构的数据(信号源数据)
(1)先了解一下数据集
S = mglearn.datasets.make_signals()
plt.figure(figsize=(10,2))
plt.plot(S,'-')
plt.xlabel("Time")
plt.ylabel("Signal")

print(S.shape)
print(S)
#输出
(2000, 3)
[[2.65408203 2.48908887 1.07757433]
[2.94981947 3.45507031 0.79929765]
[2.97649958 3.65235694 0.73473133]
...
[2.22337048 1.33481395 4.31421863]
[2.36722058 1.56522921 4.53698235]
[1.77945297 1.62362822 0.47660599]]
- 可以看出该数据具有2000条,每条有对应三个信号源的数据
(2)将混合信号分解为原始分量
我们假设有100台测量装置来观测混合信号,得到了2000条具有100维特征的信号数据X
#将数据混合成100维的状态
A = np.random.RandomState(0).uniform(size=(100,3))
X = np.dot(S,A.T)
print(X)
print(X.shape)
应用NMF还原这个混合信号
#用nmf还原这三个信号被混合成100维的信号X nmf = NMF(n_components=3,random_state=42)
S_nmf =nmf.fit_transform(X) #用于对比的pca pca = PCA(n_components=3,random_state=42)
S_pca = pca.fit_transform(X) #S_pca就是H #画图 models = [X,S,S_nmf,S_pca]
names = ["Obsevations(first measurements)",
"Ture sourses",
"NMF recovered signals",
"PCA recovered signals"] fig, axes = plt.subplots(4,figsize=(10,5),gridspec_kw={'hspace':.5},subplot_kw={'xticks':(),'yticks':()}) for model,name,ax in zip(models,names,axes):
ax.set_title(name)
ax.plot(model,'-')

- NMF在发现原始信号源时得到了不错的结果,而PCA失败了(PCA不适合这种叠加数据结构)
- NMF生成的分量是没有顺序的,如果分量顺序和原始信号完全相同(线的颜色)只是偶然。
4、参考文献
《Pyhon机器学习基础教程》P120-P126
降维、特征提取与流形学习--非负矩阵分解(NMF)的更多相关文章
- 非负矩阵分解NMF
http://blog.csdn.net/pipisorry/article/details/52098864 非负矩阵分解(NMF,Non-negative matrix factorization ...
- 文本主题模型之非负矩阵分解(NMF)
在文本主题模型之潜在语义索引(LSI)中,我们讲到LSI主题模型使用了奇异值分解,面临着高维度计算量太大的问题.这里我们就介绍另一种基于矩阵分解的主题模型:非负矩阵分解(NMF),它同样使用了矩阵分解 ...
- 【代码更新】单细胞分析实录(21): 非负矩阵分解(NMF)的R代码实现,只需两步,啥图都有
1. 起因 之前的代码(单细胞分析实录(17): 非负矩阵分解(NMF)代码演示)没有涉及到python语法,只有4个python命令行,就跟Linux下面的ls grep一样的.然鹅,有几个小伙伴不 ...
- 浅谈隐语义模型和非负矩阵分解NMF
本文从基础介绍隐语义模型和NMF. 隐语义模型 ”隐语义模型“常常在推荐系统和文本分类中遇到,最初来源于IR领域的LSA(Latent Semantic Analysis),举两个case加快理解. ...
- 推荐算法——非负矩阵分解(NMF)
一.矩阵分解回想 在博文推荐算法--基于矩阵分解的推荐算法中,提到了将用户-商品矩阵进行分解.从而实现对未打分项进行打分. 矩阵分解是指将一个矩阵分解成两个或者多个矩阵的乘积.对于上述的用户-商品矩阵 ...
- 单细胞分析实录(17): 非负矩阵分解(NMF)代码演示
本次演示使用的数据来自2017年发表于Cell的头颈鳞癌单细胞文章:Single-Cell Transcriptomic Analysis of Primary and Metastatic Tumo ...
- 数据降维-NMF非负矩阵分解
1.什么是非负矩阵分解? NMF的基本思想可以简单描述为:对于任意给定的一个非负矩阵V,NMF算法能够寻找到一个非负矩阵W和一个非负矩阵H,使得满足 ,从而将一个非负的矩阵分解为左右两个非负矩阵的乘积 ...
- 机器学习--K折交叉验证和非负矩阵分解
1.交叉验证 交叉验证(Cross validation),交叉验证用于防止模型过于复杂而引起的过拟合.有时亦称循环估计, 是一种统计学上将数据样本切割成较小子集的实用方法. 于是可以先在一个子集上做 ...
- 非负矩阵分解(4):NMF算法和聚类算法的联系与区别
作者:桂. 时间:2017-04-14 06:22:26 链接:http://www.cnblogs.com/xingshansi/p/6685811.html 声明:欢迎被转载,不过记得注明出处 ...
随机推荐
- 一行代码让微信小程序支持 cookie
weapp-cookie 一行代码让微信小程序支持 cookie,传送门:github Intro 微信原生的 wx.request 网络请求接口并不支持传统的 Cookie,但有时候我们现有的后端接 ...
- vue重构--H5--canvas实现粒子时钟
上一篇文章讲解了如何用js+canvas实现粒子时钟,本篇文章 ,主要是使用vue重构,让它在vue也能使用. 我们使用简单的方式重构,不使用vue工程,先加入vue cdn的地址,如下: <s ...
- [ Shell ] 通过 Shell 脚本导出 CDL 网表
https://www.cnblogs.com/yeungchie/ 通过 si 导出电路网表,实际上在 Virtuoso 中通过 export - cdl 和 Calibre LVS 的步骤中也是通 ...
- 如何利用MHA+ProxySQL实现读写分离和负载均衡
摘要:本文分享一下"MHA+中间件ProxySQL"如何来实现读写分离+负载均衡的相关知识. 本文分享自华为云社区<MySQL高可用架构MHA+ProxySQL实现读写分离和 ...
- python---100以内所有素数
def get_primes(): """ 100以内的所有素数:每个数都对从2到其本身前一个数做整除, 遇到能整除就换下一个数. 如果从2到去本身前一个数都没有整除,则 ...
- 网络编程学习——Linux epoll多路复用模型
前言 后端开发的应该都知道Nginx服务器,Nginx是一个高性能的 HTTP 和反向代理服务器,也是一个 IMAP/POP3/SMTP 代理服务器.后端部署中一般使用的就是Nginx反向代理技术. ...
- python3拉勾网爬虫之(您操作太频繁,请稍后访问)
你是否经历过这个:那就对了~因为需要post和相关的cookie来请求~所以,一个简单的代码爬拉钩~~~
- Java第十五周作业
Cola公司的雇员分为以下若干类:(知识点:多态) [必做题]• 4.1 ColaEmployee :这是所有员工总的父类,属性:员工的姓名,员工的生日月份.方法:getSalary(int mont ...
- CVPR 2022数据集汇总|包含目标检测、多模态等方向
前言 本文收集汇总了目前CVPR 2022已放出的一些数据集资源. 转载自极市平台 欢迎关注公众号CV技术指南,专注于计算机视觉的技术总结.最新技术跟踪.经典论文解读.CV招聘信息. M5Produc ...
- centos下安装ansible自动化工具(超详细,包含基本使用)
ansible官网:https://www.ansible.com 众所周知,ansible是新出现的自动化运维工具,基于Python开发,集合了众多运维工具(puppet.cfengine.chef ...