SVMs建立自己的垃圾邮件过滤器

        在信息化高度发达的今天,电子邮件已经成为日常通信的重要工具。然而,垃圾邮件的泛滥极大地影响了用户体验和信息安全。因此,构建一个高效的垃圾邮件过滤系统变得尤为重要。本文将介绍如何使用支持向量机(SVM)来实现一个简单而高效的垃圾邮件分类器,并详细解析相关的实现过程和核心技术。

一、项目目标

本项目的目标是基于已标注的数据集训练一个垃圾邮件分类器。该分类器可以:

1.识别一封邮件是否为垃圾邮件

2.对新输入的邮件内容做出分类判断

二、SVM 简介

1. 什么是支持向量机(SVM)

支持向量机(Support Vector Machine)是一种二分类监督学习算法,主要用于分类问题,也可以通过扩展用于回归。

它的基本目标是: 在特征空间中找到一个最优的超平面,将正类和负类分开,并最大化两类样本到这个超平面的距离。

2. 几何解释:最优超平面与间隔

假设我们在二维空间中进行分类,正类和负类可以用一条直线(超平面)分开。SVM 不仅要找到能分开两类的数据的“任意一条线”,而是要找到“离两类样本最远”的那一条。这样的分界线就是最优超平面。

支持向量:最靠近分界线的样本点,它们决定了超平面的位置

间隔(Margin):支持向量到超平面的距离,SVM 追求最大化这个间隔

3. 线性 SVM 的数学形式

我们要找到一个超平面:

使得满足:

并最大化间隔 2/∣∣w∣∣​,等价于最小化目标函数: 

这是硬间隔 SVM的形式,仅适用于完全线性可分的数据。 

4. 软间隔与 C 参数

在现实中,数据往往不能完全线性可分。为了容忍部分样本分类错误,引入“松弛变量” ξi​,得到:

C 是惩罚因子:越大越不容许分类错误;越小则允许更多误分,但具有更好泛化能力 

5. 核函数与非线性 SVM

当数据无法线性分割时,SVM 使用核函数将数据映射到高维空间,在高维空间里再进行线性分类。 

三、数据预处理与特征提取 

1. 邮件预处理流程

我们对邮件内容进行如下处理:

转小写

去除 HTML 标签

用通用占位符替换 URL、数字、邮箱地址、美元符号

分词(Tokenization)

去停用词(如 "the", "is", "in" 等)

词干提取(Stemming),保留词根

 

#1. 邮件预处理函数
def process_email(email_contents):
    #转为小写
    email_contents = email_contents.lower()

    #去除所有 HTML 标签
    email_contents = re.sub('<[^<>]+>', ' ', email_contents)

    #处理数字、网址、邮箱地址和美元符号
    email_contents = re.sub('[0-9]+', 'number', email_contents)
    email_contents = re.sub('(http|https)://[^\s]*', 'httpaddr', email_contents)
    email_contents = re.sub('[^\s]+@[^\s]+', 'emailaddr', email_contents)
    email_contents = re.sub('[$]+', 'dollar', email_contents)

    #分词并词干提取
    stemmer = PorterStemmer()
    tokens = re.split('[ @$/#.-:&*+=\[\]?!(){},\'\">_<;%\n\r]', email_contents)
    words = []

    for token in tokens:
        token = re.sub('[^a-zA-Z0-9]', '', token)
        if len(token) < 1 or token in stopwords.words('english'):
            continue
        words.append(stemmer.stem(token))

    return words

2. 构建词汇表

我们将出现频率较高的单词汇总成一个词汇表,并为每个词分配一个索引。这个词汇表是后续特征向量化的依据。

# 2. 构建词汇表
def get_vocab_list():
    vocab = {}
    with open(r"C:\Users\26687\Desktop\test\deep learning\e6\svm_data\data\vocab.txt", "r") as f:
        for line in f:
            index, word = line.strip().split('\t')
            vocab[word] = int(index)
    return vocab

3. 向量化邮件内容

将处理后的单词映射为固定长度的0/1向量,表示该词是否出现在邮件中(词袋模型)

#3. 将处理后的邮件内容转换为特征向量
def email_features(email_words, vocab_dict):
    n = len(vocab_dict)
    features = np.zeros(n)
    for word in email_words:
        if word in vocab_dict:
            index = vocab_dict[word] - 1  # 词汇表索引从 1 开始
            features[index] = 1
    return features

四、模型训练与测试

使用 SciPy 提供的 .mat 数据文件加载训练数据,并用 scikit-learn 中的 SVC 类来训练 SVM 模型

训练过程:

#训练 SVM 模型
model = svm.SVC(C=0.1, kernel='linear')
model.fit(X, y)

五、新邮件预测

可以读取新邮件文件,对其进行同样的预处理,然后输入训练好的模型进行预测:

    #预测新邮件是否为垃圾邮件
    with open(r'C:\Users\26687\Desktop\test\deep learning\e6\svm_data\data\emailSample1.txt', 'r') as file:
        content = file.read()

    words = process_email(content)
    x = email_features(words, vocab)
    pred = model.predict([x])
    print("该邮件被分类为:", "垃圾邮件" if pred[0] == 1 else "非垃圾邮件")

 

声明:本博客仅为个人理解,如有错误,敬请谅解并指出

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值