ML-For-Beginners 第 6 模块 NLP 课程:常见自然语言处理任务与 TextBlob 实战指南
【免费下载链接】ML-For-Beginners12 weeks, 26 lessons, 52 quizzes, classic Machine Learning for all项目地址: https://gitcode.com/GitHub_Trending/ml/ML-For-Beginners
自然语言处理(NLP)是机器学习在生产软件中最成熟的应用领域之一。本文以 ML-For-Beginners 课程第 6 模块「NLP 常见任务与技术」(对应仓库 6-NLP/2-Tasks/README.md)为主体,系统讲解从分词、词嵌入、句法分析到情感分析、N-gram、名词短语提取等核心任务,并结合仓库提供的 TextBlob 机器人示例源码,演示如何用 Python 库将"读懂意图与情绪"落地为可运行的对话程序。读完本文,你将掌握 NLP 任务的标准处理链路,并能独立实现一个具备情感感知与名词短语追问能力的聊天机器人。
课程定位:NLP 模块中的第二节
在 ML-For-Beginners 课程中,第 6 模块「Getting started with natural language processing」以欧洲语言与文学、欧洲浪漫酒店评论为主题,通过构建小型对话机器人来学习 NLP 基础知识(见 6-NLP/README.md)。整个模块共 5 节课:
- 自然语言处理导论(本文的前置课程,讲述 NLP 历史、计算语言学与图灵测试)
- 常见 NLP 任务与技术(本文主体)
- 机器学习的翻译与情感分析
- 数据准备(酒店评论)
- NLTK 情感分析
本文课程延续了"回到 1813 年,与简·奥斯汀《傲慢与偏见》中的伊丽莎白·班纳特和达西先生对话"的叙事线索,所有教学图示均取材自该小说句子。前序课程 1-Introduction-to-NLP/README.md 提到:人类语言的"意义理解"(尤其是幽默、反讽等情绪识别)是 NLP 中最困难的问题之一,而本文正是为解决这一问题提供可操作的"任务工具箱"。
环境准备:本文所有代码基于Python 3.8,推荐使用 Visual Studio Code + Python 扩展。课程依赖 TextBlob 简化文本处理,安装并下载语料库的命令为(见 前序课程环境说明):
pip install -U textblob python -m textblob.download_corpora
常见 NLP 任务概览
对于大多数 NLP 任务而言,待处理的文本必须先被拆解(broken down)、检查(examined),随后将结果存储(stored)或与规则和数据集交叉比对(cross referenced)。这一系列任务让开发者得以从文本中推导出词汇的含义(meaning)、意图(intent),或仅仅是频率(frequency)。
这些任务通常按固定顺序依次执行,形成一个标准处理流水线。下面逐一展开。
Tokenization:分词
大多数 NLP 算法的第一步,几乎都是将文本切分为token(记号)或单词。听起来简单,但必须考虑标点符号,以及不同语言各异的词界与句界分隔规则,因此可能相当棘手——你可能需要采用多种方法来确定切分边界。
比如上图中的句子被切分为Angry / people / are / not / always / wise这样的独立词单元。分词是后续几乎所有任务(词性标注、词频统计、N-gram 等)的输入前提。
Embeddings:词嵌入
词嵌入(Word Embeddings)是将文本数据转化为数值表示的方法,其核心设计是让语义相近的词或常搭配使用的词在向量空间中彼此聚集(cluster)。正如上图所示,"respect"、"nerves"、"old friends" 等词被分入不同语义集群,集群之间通过关联箭头连接,隐喻词向量空间中的相似度关系。
✅ 动手实验:可以尝试 TensorFlow Projector 这个在线工具体验词嵌入。点击任意一个词,它会展示与之聚类的相似词——例如 'toy' 会与 'disney'、'lego'、'playstation'、'console' 聚在一起。
词嵌入的价值在于把离散的、计算机无法直接计算的词语,转换为连续的、可进行算术与相似度运算的向量,是后续机器学习建模的基础。
Parsing 与词性标注(Part-of-Speech Tagging)
每一个被分词的单词都可以被标注为一种词性(Part of Speech,POS)——例如名词、动词或形容词。对句子the quick red fox jumped over the lazy brown dog,可标注为:fox = 名词,jumped = 动词。
Parsing(句法分析)则更进一步,用于识别句子中哪些词彼此存在语法关系。例如the quick red fox jumped是一个与lazy brown dog序列相互独立的"形容词-名词-动词"序列。上图展示了《傲慢与偏见》中 "Elizabeth was too much embarrassed to say a word." 的标注结果:Elizabeth 被标为专有名词(proper noun),was 标为动词(verb),too much embarrassed 标为形容词(adjective),to say 标为不定式动词(v. infinitive)——这就是词性标注与句法分析在真实句子上的直观呈现。
Parsing 与 POS 标注是让计算机"像人一样读懂句子结构"的基石,也是前序课程中"计算机非常擅长应用形式规则"这一论断的具体体现。
词与短语频率统计(Word and Phrase Frequencies)
分析大规模文本语料时,一个非常实用的做法是构建字典,统计每个感兴趣的词或短语出现了多少次。例如the quick red fox jumped over the lazy brown dog中,词 "the" 的词频为 2。
来看一个统计词频的真实示例——拉迪亚德·吉卜林(Rudyard Kipling)的诗歌《The Winners》中的一节:
What the moral? Who rides may read. When the night is thick and the tracks are blind A friend at a pinch is a friend, indeed, But a fool to wait for the laggard behind. Down to Gehenna or up to the Throne, He travels the fastest who travels alone.短语频率可以按需设置为区分大小写或不区分大小写。按上述文本统计:短语a friend的频率为 2,"the" 的频率为 6,"travels" 的频率为 2。这种统计是文本挖掘、关键词提取、主题分析等信息检索任务的基础。
N-Gram:n 元语法
文本可以按固定长度切分为词序列:单个词称为Unigram(一元语法),两个词为Bigram(二元语法),三个词为Trigram(三元语法),任意数量的词统称N-gram(n 元语法)。
以the quick red fox jumped over the lazy brown dog为例,n-gram 值取 2 时得到如下二元语法:
- the quick
- quick red
- red fox
- fox jumped
- jumped over
- over the
- the lazy
- lazy brown
- brown dog
更直观的方式是把 n-gram 想象成在句子上滑动的窗口。下面是 n-gram 值为 3(Trigram)时,窗口逐词滑动的完整过程(加粗下划线即为当前的 trigram):
- the quick redfox jumped over the lazy brown dog
- thequick red foxjumped over the lazy brown dog
- the quickred fox jumpedover the lazy brown dog
- the quick redfox jumped overthe lazy brown dog
- the quick red foxjumped over thelazy brown dog
- the quick red fox jumpedover the lazybrown dog
- the quick red fox jumped overthe lazy browndog
- the quick red fox jumped over thelazy brown dog
N-gram 滑动窗口动画见仓库图片 n-grams.gif:窗口沿句子依次后移,每一步高亮一个新的连续 n 词序列。N-gram 是语言建模、拼写纠错、文本自动补全等任务的核心工具。
名词短语提取(Noun Phrase Extraction)
大多数句子中都存在一个作为主语(subject)或宾语(object)的名词。在英语中,它通常以 'a'、'an' 或 'the' 冠词前置为特征。通过提取名词短语来识别句子主语或宾语,是 NLP 中理解句子含义时的常见任务。
在句子the quick red fox jumped over the lazy brown dog中有2 个名词短语:quick red fox和lazy brown dog。
✅ 练习:你能识别下面这个句子中的名词短语吗?
"I cannot fix on the hour, or the spot, or the look or the words, which laid the foundation. It is too long ago. I was in the middle before I knew that I had begun."
名词短语提取让机器人能够抓住对话的"话题对象",是本文后半部分 Marvin 机器人追问"tell me more about ..."的关键机制。
情感分析(Sentiment Analysis)
一个句子或文本可以被分析出其情绪(sentiment),即它有多积极(positive)或多消极(negative)。情感通常用两个维度度量:
- 极性(Polarity):取值范围-1.0 到 1.0(负向到正向);
- 客观性/主观性(Objectivity/Subjectivity):取值范围0.0 到 1.0(最客观到最主观)。
✅ 理解:后面你会学到用机器学习判断情感有多种方式,其中一种朴素实现是:由人类专家维护一份"积极/消极词与短语清单",将该模型套用到文本上计算极性得分。你能看出这种方法在哪些场景下有效、哪些场景下效果不佳吗?(例如反讽、双关等语境会让纯词表法失效。)
情感分析是本文实战机器人的核心能力——通过TextBlob.polarity阈值分级,机器人可以对用户输入做出"共情"回应。
屈折变化(Inflection)与词形还原(Lemmatization)
- 屈折变化(Inflection):让你取一个词并获得其单数或复数形式(如 cat → cats)。它是让机器人追问话题时语言自然化的关键,例如把 "lovely cat" 变成 "lovely cats"。
- 词形还原(Lemmatization):词元(lemma)是一组词的基本形式或词头(root / headword)。例如flew(飞,过去式)、flies(飞,三单)、flying(飞,进行时)的词元都是动词fly。
此外,NLP 研究者还有重要的数据库资源:
WordNet
WordNet 是一个包含多种语言中每个单词的词、同义词、反义词以及大量其他细节的数据库。在构建翻译工具、拼写检查器或任何类型的语言工具时,它都极其有用。
NLP 库:用 TextBlob 简化一切
幸运的是,你不必从零实现上述所有技术——现成的优秀 Python 库让非 NLP/机器学习专业背景的开发者也能轻松上手。后续课程会展示更多示例,这里先学习对下一个任务最有用的部分:TextBlob。
TextBlob 之所以好用,正如其官方描述:它"站在 NLTK 与 pattern 的巨人之肩上,并与两者良好协作",其 API 中内嵌了相当可观的机器学习能力。经验丰富的 Python 开发者可以参考 TextBlob 官方的 Quick Start 指南快速上手。
练习:使用ConllExtractor提取名词短语
当需要识别名词短语时,TextBlob 提供多种提取器(extractor)可选。本课程重点介绍ConllExtractor:
from textblob import TextBlob from textblob.np_extractors import ConllExtractor # import and create a Conll extractor to use later extractor = ConllExtractor() # later when you need a noun phrase extractor: user_input = input("> ") user_input_blob = TextBlob(user_input, np_extractor=extractor) # note non-default extractor specified np = user_input_blob.noun_phrases这里发生了什么?ConllExtractor是"一个使用ConLL-2000 训练语料训练的 chunk parsing(组块解析)名词短语提取器"。ConLL-2000 指 2000 年召开的Conference on Computational Natural Language Learning(计算自然语言学习会议)。该会议每年举办工作坊攻克一个棘手的 NLP 问题,2000 年的题目正是名词组块(noun chunking)。当时的模型使用《华尔街日报》语料训练:第 15–18 节作为训练数据(211,727 个 token),第 20 节作为测试数据(47,377 个 token)。课程还提供了当年的使用流程与评测结果供深入研究。
注意代码中的注释:np_extractor=extractor指定的是非默认提取器——TextBlob 允许开发者替换默认的名词短语提取策略,这是其 API 灵活性的体现。
实战挑战:用 NLP 改进你的机器人(Marvin)
前序课程中你构建了一个非常简单的问答机器人。现在,通过情感分析与名词短语识别让 Marvin 变得更"善解人意":分析输入的情绪并输出匹配的回应,同时识别出noun_phrase并围绕它追问。
构建更好对话机器人的步骤:
- 打印指令,告知用户如何与机器人交互;
- 进入循环:
- 接受用户输入;
- 若用户请求退出,则退出;
- 处理用户输入,确定合适的情感回应;
- 若在输入中检测到名词短语,将其复数化并围绕该话题追问更多信息;
- 打印回应;
- 回到第 2 步继续循环。
用 TextBlob 判定情感
下面是使用 TextBlob 判定情感的代码片段。注意这里只设置了四个情感回应梯度(你可以按需增加更多):
if user_input_blob.polarity <= -0.5: response = "Oh dear, that sounds bad. " elif user_input_blob.polarity <= 0: response = "Hmm, that's not great. " elif user_input_blob.polarity <= 0.5: response = "Well, that sounds positive. " elif user_input_blob.polarity <= 1: response = "Wow, that sounds great. "这段阈值逻辑与仓库提供的完整解决方案 6-NLP/2-Tasks/solution/bot.py 完全一致,可以作为可复制的参照实现。
完整解决方案解读
仓库 solution/bot.py 给出了可直接运行的标准答案。拆解其实现要点:
- 初始化提取器(L3-L4):在模块级创建
extractor = ConllExtractor()实例,供整个会话复用,避免重复加载模型; - 退出逻辑(L16-L18):
user_input.lower() == "bye"通过统一转小写,兼容BYE、ByE等各种大小写写法; - 名词短语提取(L21-L22):
TextBlob(user_input, np_extractor=extractor)构建 blob,noun_phrases属性返回短语列表; - 复数化追问(L33-L38):若检测到至少一个名词短语,取第一个短语执行
np[0].pluralize()(如 cat → cats、mouse → mice),生成 "Can you tell me more about lovely cats?" 句式;否则退化为通用追问 "Can you tell me more?"。
参考输出示例
下面是课程给出的示例会话(以>开头的行是用户输入):
Hello, I am Marvin, the friendly robot. You can end this conversation at any time by typing 'bye' After typing each answer, press 'enter' How are you today? > I am ok Well, that sounds positive. Can you tell me more? > I went for a walk and saw a lovely cat Well, that sounds positive. Can you tell me more about lovely cats? > cats are the best. But I also have a cool dog Wow, that sounds great. Can you tell me more about cool dogs? > I have an old hounddog but he is sick Hmm, that's not great. Can you tell me more about old hounddogs? > bye It was nice talking to you, goodbye!注意观察:机器人不仅根据极性(0.5 阈值)给出四种梯度回应,还会把 "a lovely cat" 复数化为 "lovely cats"、把 "a cool dog" 变成 "cool dogs" 进行话题追问——这正是"情感 + 名词短语 + 屈折变化"三项任务组合的实战效果。
✅ 知识检查
- 你认为这些共情式回应能否"骗过"别人,让他们以为机器人真的理解了自己?
- 识别名词短语是否让机器人显得更"可信"?
- 为什么从句子中提取"名词短语"是一件有用的事?
作业:让机器人开口回话
本课作业详见 6-NLP/2-Tasks/assignment.md:在之前课程中你编写了一个只能随机应答、直到你说 'bye' 才结束的基础聊天机器人。请尝试让回答不那么随机——当你说出特定词语(如 'why' 或 'how')时触发针对性回答。同时思考:随着机器人不断扩展,机器学习如何让这类工作减少人工维护。任务允许使用NLTK 或 TextBlob库来简化工作。
作业评分标准(Rubric):
| 标准 | 优秀(Exemplary) | 合格(Adequate) | 待改进(Needs Improvement) |
|---|---|---|---|
| 交付物 | 提交了带文档说明的新 bot.py 文件 | 提交了新 bot 文件但存在 bug | 未提交文件 |
🚀 延伸挑战
选取知识检查中的任意一项任务动手实现,然后让一位朋友来测试你的机器人:
- 它能否"骗过"朋友?
- 你能让机器人变得更"可信"吗?
复习与自研方向
在接下来的课程中,你将更深入地学习情感分析(尤其是基于酒店评论数据集的实践,见 6-NLP/4-Hotel-Reviews-1/README.md 与 6-NLP/5-Hotel-Reviews-2/README.md)。可以持续关注 KDNuggets 等平台上关于 NLP 的优质文章来追踪这一领域。结合本文所学,一条清晰的进阶路线是:先用 TextBlob 掌握任务直觉,再进入下一课学习基于机器学习的翻译与情感分析(3-Translation-Sentiment),理解词表法之外的数据驱动方案。
本文内容主体源自课程文档 6-NLP/2-Tasks/README.md(及德语翻译版 translations/de/6-NLP/2-Tasks/README.md),并辅以仓库 解决方案源码、作业说明 与 教学图示 进行印证与扩充。
【免费下载链接】ML-For-Beginners12 weeks, 26 lessons, 52 quizzes, classic Machine Learning for all项目地址: https://gitcode.com/GitHub_Trending/ml/ML-For-Beginners
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考