{ "cells": [ { "cell_type": "markdown", "metadata": {}, "source": [ "---\n", "title: 文本向量系列-如何基于拼音构建字向量\n", "date: 2018-08-17 12:17:55\n", "tags: [python, 文本挖掘]\n", "toc: true\n", "xiongzhang: true\n", "xiongzhang_images: [main.jpg]\n", "\n", "---\n", "\n", "\n" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### 系列文章\n", "\n", "这个是系列博客, 所有文章链接都列在这里, 并持续更新中。\n", "\n", "" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "用拼音来表示字向量的方法我见的比较少, 也没有见过类似的研究, 我这里只是介绍一下这个方法, 但是并不能评价这个方法的好坏. 在一些英文语料的研究中见过一些研究者使用字母来形成词向量的, 因为总共有26个英文字母, 所以一个词/拼音可以表示为26维的字母频率向量。\n", "\n", "我们使用的开发环境:\n", "\n", "- jupyter notebook\n", "- python3.6\n", "\n", "### 算法\n", "\n", "主要包括两个步骤:\n", "\n", "- 汉字转拼音\n", "- 获取唯一字符集\n", "- 拼音向量化" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### 使用pypinyin工具进行汉字转拼音\n", "\n", "\n", "安装方法:\n", "\n", "```\n", "pip install pypinyin\n", "```" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "#### 基本用法" ] }, { "cell_type": "code", "execution_count": 3, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "[['wǒ'], ['ài'], ['nǐ'], ['zhōng'], ['guó']]" ] }, "execution_count": 3, "metadata": {}, "output_type": "execute_result" } ], "source": [ "from pypinyin import pinyin\n", "pinyin('我爱你中国')" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### 使用测试语料库\n", "\n", "我们可以看到, 输出的是带有声调的拼音, 假设我不知道总共有多少种不同的字符构成了拼音(实际上是可以算出来的), 因为很多情况下我们都是根据语料库来确定的, 只要字符数量足够大能够表征我们的语料库就可以了, 所以我们需要一个语料库。\n", "\n", "我们假设使用下面的语料库:\n", "\n", "```\n", "随着互联网, 尤其是移动互联网的快速发展, 社交媒体已经变成人们交流和传递思想的主要平台。每天从社交平台上产生的信息交互量难以估计。面对如此海量的消息, 如何进行科学的有效管理, 已成为当前的研究热点。根据中国互联网发展统计报告, 文本信息已占网络资源的70%以上, 是互联网中信息传播的主要载体, 每天从网络中产生的文本信息量在TB级别以上。在文本处理领域, 一般将文本信息分为长文本和短文本。互联网产生的数据大多数以短文本为主, 如腾讯空间说说、新浪微博、百度知识问答和淘宝商品的评价等。相对于传统大篇幅的长文本, 人们更容易接受以短文本的形式进行交流。如新浪微博限制其消息字数为140, 知识问答都是以简略语句的形式来概括。短文本能更好的表达出人们的情绪, 人们更喜欢以几个字甚至一个表情来表达自己的情感倾向。如何使用机器学习的相关方法对这些数据进行分析, 挖掘出有用的信息, 从而更好的利用互联网改善人民的生活已经变得日趋重要, 如帮助商家提供决策, 以使其利益最大化, 帮助用户更有效的提高产品体验, 是当前文本挖掘的重要课题。\n", "```\n", "注意, 我们的语料库还包括标点符号和数字, 我们把这些符号也当作\"字\"来进行向量化。" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### 获取所有不同的字符(字符集)\n", "\n", "在文本处理的工作中, 经常会用到词典(语料库包含的所有词的集合), 我们现在也要先找到这个\"词典\", 姑且就叫他字符集。每个字符对应一个整数作为他的ID。\"字典\"的作用就是可以将字符/词与数字进行互转。" ] }, { "cell_type": "code", "execution_count": 11, "metadata": { "scrolled": false }, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "Counter({'n': 173, 'g': 95, 'h': 82, 'i': 67, 'd': 47, 'x': 38, 'u': 37, 'é': 37, 'ǎ': 35, 'y': 35, 'ì': 34, 'à': 34, 's': 33, 'ā': 30, 'j': 30, 'z': 29, 'w': 29, 'í': 27, 'e': 26, 'ǐ': 26, 'b': 26, 'ù': 23, 'l': 23, 'á': 23, 'o': 23, 'ī': 19, ',': 18, ' ': 18, 'è': 18, 'c': 17, 'r': 15, 't': 14, 'ě': 14, 'ē': 12, 'q': 11, 'ò': 11, 'ú': 10, '。': 10, 'ō': 10, 'ó': 9, 'm': 9, 'f': 7, 'p': 6, 'k': 5, 'ǔ': 5, 'ū': 5, 'ǒ': 5, '0': 2, '、': 2, '7': 1, '%': 1, 'T': 1, 'B': 1, '1': 1, '4': 1, 'ü': 1})\n" ] } ], "source": [ "from itertools import chain\n", "from collections import Counter\n", "\n", "text = '''随着互联网, 尤其是移动互联网的快速发展, 社交媒体已经变成人们交流和传递思想的主要平台。每天从社交平台上产生的信息交互量难以估计。面对如此海量的消息, 如何进行科学的有效管理, 已成为当前的研究热点。根据中国互联网发展统计报告, 文本信息已占网络资源的70%以上, 是互联网中信息传播的主要载体, 每天从网络中产生的文本信息量在TB级别以上。在文本处理领域, 一般将文本信息分为长文本和短文本。互联网产生的数据大多数以短文本为主, 如腾讯空间说说、新浪微博、百度知识问答和淘宝商品的评价等。相对于传统大篇幅的长文本, 人们更容易接受以短文本的形式进行交流。如新浪微博限制其消息字数为140, 知识问答都是以简略语句的形式来概括。短文本能更好的表达出人们的情绪, 人们更喜欢以几个字甚至一个表情来表达自己的情感倾向。如何使用机器学习的相关方法对这些数据进行分析, 挖掘出有用的信息, 从而更好的利用互联网改善人民的生活已经变得日趋重要, 如帮助商家提供决策, 以使其利益最大化, 帮助用户更有效的提高产品体验, 是当前文本挖掘的重要课题。'''\n", "zi = chain(*pinyin(text))\n", "chars = chain(*zi)\n", "char_counts = Counter(chars)\n", "print(char_counts)" ] }, { "cell_type": "code", "execution_count": 12, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "[' ', '%', ',', '0', '1', '4', '7', 'B', 'T', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'w', 'x', 'y', 'z', 'à', 'á', 'è', 'é', 'ì', 'í', 'ò', 'ó', 'ù', 'ú', 'ü', 'ā', 'ē', 'ě', 'ī', 'ō', 'ū', 'ǎ', 'ǐ', 'ǒ', 'ǔ', '、', '。']\n" ] } ], "source": [ "# 求所有的字符\n", "unique_chars = sorted(char_counts.keys())\n", "print(unique_chars)" ] }, { "cell_type": "code", "execution_count": 14, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "{' ': 0,\n", " '%': 1,\n", " ',': 2,\n", " '0': 3,\n", " '1': 4,\n", " '4': 5,\n", " '7': 6,\n", " 'B': 7,\n", " 'T': 8,\n", " 'b': 9,\n", " 'c': 10,\n", " 'd': 11,\n", " 'e': 12,\n", " 'f': 13,\n", " 'g': 14,\n", " 'h': 15,\n", " 'i': 16,\n", " 'j': 17,\n", " 'k': 18,\n", " 'l': 19,\n", " 'm': 20,\n", " 'n': 21,\n", " 'o': 22,\n", " 'p': 23,\n", " 'q': 24,\n", " 'r': 25,\n", " 's': 26,\n", " 't': 27,\n", " 'u': 28,\n", " 'w': 29,\n", " 'x': 30,\n", " 'y': 31,\n", " 'z': 32,\n", " 'à': 33,\n", " 'á': 34,\n", " 'è': 35,\n", " 'é': 36,\n", " 'ì': 37,\n", " 'í': 38,\n", " 'ò': 39,\n", " 'ó': 40,\n", " 'ù': 41,\n", " 'ú': 42,\n", " 'ü': 43,\n", " 'ā': 44,\n", " 'ē': 45,\n", " 'ě': 46,\n", " 'ī': 47,\n", " 'ō': 48,\n", " 'ū': 49,\n", " 'ǎ': 50,\n", " 'ǐ': 51,\n", " 'ǒ': 52,\n", " 'ǔ': 53,\n", " '、': 54,\n", " '。': 55}" ] }, "execution_count": 14, "metadata": {}, "output_type": "execute_result" } ], "source": [ "# 构建词典\n", "dictionary = dict(zip(unique_chars, range(len(unique_chars))))\n", "dictionary" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### 计算字向量\n", "\n", "现在我们已经准备好了所有形成字向量需要用到的基本条件, 下面我们开始:" ] }, { "cell_type": "code", "execution_count": 22, "metadata": {}, "outputs": [ { "data": { "text/plain": [ "array([0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 1., 1., 0.,\n", " 0., 0., 0., 0., 1., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 1., 0.,\n", " 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 1.,\n", " 0., 0., 0., 0., 0.])" ] }, "execution_count": 22, "metadata": {}, "output_type": "execute_result" } ], "source": [ "import numpy as np\n", "def vectorize(word, dictionary):\n", " # 字转拼音\n", " chars = pinyin(word)[0][0]\n", " # 统计拼音中出现的字符个数\n", " counts = Counter(chars)\n", " # 构建一个0向量\n", " vector = np.zeros((len(dictionary)))\n", " # 使用字符频率给向量元素赋值\n", " for char, cnt in counts.items():\n", " index = dictionary[char]\n", " vector[index]=cnt\n", " return vector\n", " \n", "vectorize('长', dictionary)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "### 总结\n", "\n", "这篇教程的主要用到了汉字转拼音的模块: pypinyin, 不过只用到了这个模块的其中一个功能。\n", "\n", "字拼音向量化的思想主要是统计每个可能字符的频率, 所有字符的频率按照顺序组合到一起就构成了字的向量。\n", "\n", "作为实战的第一篇, 这个教程比较简单啦, 只要python入门了就能看懂, 后面可能会逐步增加难度。" ] } ], "metadata": { "kernelspec": { "display_name": "Python 3", "language": "python", "name": "python3" }, "language_info": { "codemirror_mode": { "name": "ipython", "version": 3 }, "file_extension": ".py", "mimetype": "text/x-python", "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", "version": "3.6.4" } }, "nbformat": 4, "nbformat_minor": 2 }