使用 ICA 消除 EEG 信号中的眨眼现象

2024-04-09

我是 scikit-learn 的新手,但我正在尝试消除单个脑电图通道内的眨眼(噪声峰值)。 我在互联网上搜索过,但只看到了 MNE、PyEEG 或其他 Python 模块的更复杂的读物。我只想要一些简单的东西并且只依赖于sklearn。这是我的代码:

#The channel containing some eye-blinks
X = f1ep1_data[:,[4]]

#run ICA on signal
ica = FastICA(n_components=2)
ica.fit(X)

#reconstruct signal with independent components
components = ica.fit_transform(X)
X_restored = ica.inverse_transform(components)

fig1 = plt.figure()
plt.subplot(3,1,1)
plt.title("Original signal")
plt.plot(f1ep1_timescale, X)

plt.subplot(3,1,2)
plt.title("Components")
plt.plot(f1ep1_timescale, components)

plt.subplot(3,1,3)
plt.title("Signal Reconstructed")
plt.plot(f1ep1_timescale, X_restored)
plt.draw()

我期待的是分成两个部分,更清晰的脑电图信号和眨眼。我不知道出了什么问题。有人可以伸出援助之手吗?


您是否注意到您的“组件”正是按比例缩放并颠倒的原始信号?这是因为你无法获得比信号更多的组件。

您需要执行以下步骤:

  1. feed allEEG 通道进入 ICA
  2. 手动删除包含眨眼或其他伪影的组件
  3. 使用逆变换重建

我们来详细看看第2步:为什么要手动删除组件?ICA 对眨眼一无所知。它根据统计测量将信号分离成多个分量。如果幸运的话,其中一些组件看起来就像眨眼一样。

到目前为止还好,但真正的问题是组件的顺序没有定义。运行 ICA,您可能会发现组件 1 包含眨眼。再次运行,它们位于组件 3 中。再次运行,它们位于组件 2 和 5 中...

无法提前知道要删除哪些组件以及要删除多少组件。这就是为什么您需要在每次运行时手动将其告知算法。

代码看起来像这样:

# Use all channels - they will contain eye blinks to varying degrees
X = f1ep1_data[:, :]

# run ICA on signal
ica = FastICA(n_components=x.shape[1])  # we want *all* the components
ica.fit(X)

# decompose signal into components
components = ica.fit_transform(X)

# plot components and ask user which components to remove
# ...
remove_indices = [0, 1, 3]  # pretend the user selected components 0, 1, and 3

# "remove" unwanted components by setting them to 0 - simplistic but gets the job done
components[:, remove_indices] = 0

#reconstruct signal
X_restored = ica.inverse_transform(components)

您很可能对手动步骤不满意。运气不好:) 2013 年,还没有强大的自动算法来标记眨眼组件。我不认为这已经改变,但如果有什么东西你会发现它是领域特定的软件包之一,如 MNE 或 PyEEG。


不过,如果您碰巧有眼电图记录,那就还有希望!那里存在脑电图记录中脑电图伪影的全自动校正方法 https://www.ncbi.nlm.nih.gov/pubmed/17088100。该方法基于典型相关或回归(我不记得细节),但您需要将 EOG 信号与 EEG 一起记录。


我使用模拟“EEG”数据创建了一个工作示例。 数据由三个通道组成:额叶通道、中央通道和顶叶通道。 10 Hz 阿尔法活动在后面最强,一些类似眨眼的尖峰在前面最强。

希望这个示例能够更好地说明如何从多通道数据中删除组件。

import numpy as np
import scipy.signal as sps
from sklearn.decomposition import FastICA
import matplotlib.pyplot as plt

np.random.seed(42)

n = 1000
fs = 100
noise = 3

# simulate EEG data with eye blinks
t = np.arange(n)
alpha = np.abs(np.sin(10 * t / fs)) - 0.5
alpha[n//2:] = 0
blink = np.zeros(n)
blink[n//2::200] += -1
blink = sps.lfilter(*sps.butter(2, [1*2/fs, 10*2/fs], 'bandpass'), blink)

frontal = blink * 200 + alpha * 10 + np.random.randn(n) * noise
central = blink * 100 + alpha * 15 + np.random.randn(n) * noise
parietal = blink * 10 + alpha * 25 + np.random.randn(n) * noise

eeg = np.stack([frontal, central, parietal]).T  # shape = (100, 3)

# plot original data
plt.subplot(3, 1, 1)
plt.plot(frontal + 50)
plt.plot(central + 100)
plt.plot(parietal + 150)
plt.yticks([50, 100, 150], ['Fz', 'Cz', 'Pz'])
plt.ylabel('original data')

# decompose EEG and plot components
ica = FastICA(n_components=3)
ica.fit(eeg)
components = ica.transform(eeg)

plt.subplot(3, 1, 2)
plt.plot([[np.nan, np.nan, np.nan]])  # advance the color cycler to give the components a different color :)
plt.plot(components + [0.5, 1.0, 1.5])
plt.yticks([0.5, 1.0, 1.5], ['0', '1', '2'])
plt.ylabel('components')

# looks like component #2 (brown) contains the eye blinks
# let's remove them (hard coded)!
components[:, 2] = 0

# reconstruct EEG without blinks
restored = ica.inverse_transform(components)

plt.subplot(3, 1, 3)
plt.plot(restored + [50, 100, 150])
plt.yticks([50, 100, 150], ['Fz', 'Cz', 'Pz'])
plt.ylabel('cleaned data')
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

使用 ICA 消除 EEG 信号中的眨眼现象 的相关文章

随机推荐

  • 生成数字数组中有效的数字组合

    我正在尝试从数字数组中生成所有有效的数字组合 假设我们有以下内容 let arr 1 2 9 4 7 我们需要输出这样的内容 1 2 9 4 7 1 2 9 47 1 2 94 7 1 2 947 1 29 4 7 1 29 47 1 29
  • 我无法在我的 Visual C Express Edition 2008 中汇编电影 (MMX) 指令

    当我尝试编译时movd指令显示错误为 error A2085 instruction or register not accepted in current CPU mode 我的代码如下 386 model flat c code add
  • 我怎样才能让我的verilog移位器更通用?

    这里我有一个移位器 但现在它最多只能工作 3 位 我一直在寻找 但不知道如何让它工作最多 8 位 module shifter a b out input 7 0 a b output 7 0 out wire 7 0 out1 out2
  • 扩展 Eloquent 的类的构造函数

    我刚刚启动了一个新网站 我想使用 Eloquent 在为数据库播种的过程中 我注意到 如果我在扩展 eloquent 的模型上包含任何类型的构造函数 则会添加空行 例如 运行此播种器
  • 如何解决三向多态关联?

    首先我要说我正在使用 MySQL 不是事务型 并且这是无法更改的 另外 为了简洁和清晰起见 我简化了此处的表格 在此示例中 课程 由其内部属性和外部属性及其自己的属性 阅读 组成 阅读 有其自己的关键依赖属性和三个不同的外部属性 阅读源 我
  • 如何在 SQL Server 2008 中存储特定列的列值?

    基本上我正在映射字段 正如你所看到的GridView 2我选择了特定的列名称 让我们考虑第一条记录 即1 id Column0 For id我已选择Column0 所以在数据库中我想在 id 列下存储列值 1 2 3 4 像下面这样 id
  • 使用属性和不访问 ivars 之间的区别

    使用属性或直接访问 ivars 的特定性能和行为差异 对于全局变量 使用它有什么区别 interface myClass UIImageView myView void loadView super loadView myView UIIm
  • 如何动态添加 mixin 作为基类而不出现 MRO 错误?

    说我有课A B and C Class A and B都是 Class 的 mixin 类C class A object pass class B object pass class C object A B pass 这在实例化 C 类
  • 在angularjs中克隆html元素

    我正在尝试在 angularjs 中实现拖放系统 我希望在拖动开始时克隆拖动的对象 但是我不知道如何在 angularjs 中克隆元素及其范围和链接控制器 有什么建议么 不建议使用 Angular 来克隆 DOM 元素 通常是通过拖放完成的
  • 如何比较两个 pandas 数据帧并删除一个文件上的重复项而不附加其他文件中的数据[重复]

    这个问题在这里已经有答案了 我正在尝试使用 pandas 数据框比较两个 csv 文件 其中一个是每天都会附加数据的主表 test master csv 第二个是每日报告 test daily csv 其中包含我想要附加到 test mas
  • 使用 slick/scala 进行流式传输

    我正在研究 scala slick 流 并试图了解它是如何工作的 这是我的测试代码 val bigdata TableQuery BigData val x db stream bigdata result transactionally
  • Relay vs Redux vs Apollo with GraphQL 和 React-Native [已关闭]

    Closed 这个问题是基于意见的 help closed questions 目前不接受答案 我必须从头开始一个新的 网络 本机 项目 中型应用程序 由于存在过多的 JS 框架和实现 尤其是在过去几年中 我对我常用的堆栈产生了第二个怀疑
  • axis2+rampart:必须了解标头安全检查失败

    在服务器内部错误的情况下 我对 axis2 rampart WS Security 响应有问题 当服务器返回 200 OK 时 一切似乎都正常 Rampart 检查响应是否具有正确的时间戳 签名并解密函数响应 XML 但是当服务器返回 50
  • Neo4j:检索连接到 Neo4j Rest 中的节点或通过 Cypher 的所有节点和关系

    我想检索所有节点以及连接到节点的关系 我尝试通过两种方式做到这一点 1st通过Neo4j REST API http docs neo4j org chunked milestone server java rest client exam
  • cURL 错误 60:Laravel 5.4 中的 SSL 证书

    完全错误 RequestException in CurlFactory php line 187 cURL error 60 SSL certificate problem unable to get local issuer certi
  • iOS - 加速度计的高通滤波器方程

    有人可以解释一下如何得出下面的方程来对加速度计值进行高通滤波吗 我不需要数学推导 只需要直观的解释就足够了 define kFilteringFactor 0 1 UIAccelerationValue rollingX rollingY
  • 解释了将双精度数舍入为 32 位整数的快速方法

    读书时Lua http en wikipedia org wiki Lua 28programming language 29的源码中 我注意到Lua使用了一个宏来进行舍入double值转为 32 位int价值观 该宏定义在Llimits
  • Python TKinter 多种操作

    我的窗体上有两个按钮 当我按下按钮时 它会保持按下状态 并且框架保持无响应状态 直到按钮1的操作完成为止 在我的情况下 我调用保持打开状态的新xterm窗口 并且使用按钮2我想打开新的xterm但直到我从button1命令关闭xterm窗口
  • “标准”RGB 到灰度转换

    我正在尝试编写一个转换器算法 该算法采用 JPEG 图像并返回其 PGM 便携式灰度图 版本 问题是我无法理解 官方 JPG gt PGM 转换器如何从经典 RGB 格式开始为最终像素分配什么值 我猜是 0 gt 255 一开始 我使用了这
  • 使用 ICA 消除 EEG 信号中的眨眼现象

    我是 scikit learn 的新手 但我正在尝试消除单个脑电图通道内的眨眼 噪声峰值 我在互联网上搜索过 但只看到了 MNE PyEEG 或其他 Python 模块的更复杂的读物 我只想要一些简单的东西并且只依赖于sklearn 这是我