降维、特征提取与流形学习--非负矩阵分解(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 声明:欢迎被转载,不过记得注明出处 ...
随机推荐
- react开发教程(三)组件的构建
什么是组件 组件化就好像我们的电脑装机一样,一个电脑由显示器.主板.内存.显卡.硬盘,键盘,鼠标.... 组件化开发有如下的好处:降低整个系统的耦合度,在保持接口不变的情况下,我们可以替换不同的组件快 ...
- 《深入理解ES6》笔记——块级作用域绑定(1)
本章涉及3个知识点,var.let.const,现在让我们了解3个关键字的特性和使用方法. var JavaScript中,我们通常说的作用域是函数作用域,使用var声明的变量,无论是在代码的哪个地方 ...
- 如何监控微信小程序HTTP请求错误
摘要: Fundebug的微信小程序错误监控插件更新至0.5.0,支持监控HTTP请求错误. 接入插件 接入Fundebug的错误监控插件非常简单,只需要下载fundebug.0.5.0.min.js ...
- Python窗口学习之给按钮美化
tkinter的按钮很丑也很难改 怎么办呢? 最好的方法就是不用按钮! 给Label添加点击事件,和按钮的作用是一样的! 代码: #!/usr/bin/env python # -*- coding: ...
- 在tomcat布置项目
1.将项目打成war包复制到tomcat-webapps 2.修改tomcat端口号 3.指定jdk 一.找到tomcat目录/bin 文件夹下的 catalina.bat文件 二.在文件中找到 ec ...
- Java基础之浅谈异常与了解断言
一.产生错误原因 用户输入错误 设备错误 物理限制 代码错误 二.解决错误---异常 在Java中异常对象都是派生于Throwable类的一个实例. 我们一般将异常分为两种:①Error和②Excep ...
- 基于Apache组件,分析对象池原理
池塘里养:Object: 一.设计与原理 1.基础案例 首先看一个基于common-pool2对象池组件的应用案例,主要有工厂类.对象池.对象三个核心角色,以及池化对象的使用流程: import or ...
- Springboot集成cache的key生成策略
代码接上文:深度理解springboot集成redis缓存之源码解析 ## 1.使用SpEL表达式 @Cacheable(cacheNames = "emp",key = &quo ...
- linux ping的三个数字(56,84,64)
参考:ping 深入剖析:https://www.cnblogs.com/aozhejin/p/15917312.html windows默认是32字节,linux是56字节说的都是数据包大小注意:1 ...
- CentOS7.x 离线安装和开机启动 supervisor 4.2.4
CentOS7.x 服务器 离线安装 开机启动 supervisor 4.2.4