数据来源于天池赛题:零基础入门数据分析-学术前沿趋势分析
TF-IDF方法常用来评估一字词对于一个文件集或一个语料库中的其中一份文件的重要程度。在一个特定文件中,当某类词语出现的频率较高,同时该类词语在整个语料库中出现频率较低时,该类词语的TF-IDF就会比较高。
TF-IDF在中文中指词频-逆向文件频率,由TF(词频)和IDF(逆向文件频率)两个部分组成。
其中,TF(词频)指的是某一个给定的词语在该文件中出现的次数,TF的计算公式为:
T F w = 在 某 一 类 中 词 条 w 出 现 的 次 数 该 类 中 所 有 的 词 条 数 目 TF_{w}=\frac{在某一类中词条w出现的次数}{该类中所有的词条数目} TFw=该类中所有的词条数目在某一类中词条w出现的次数
IDF(逆向文件频率)的主要思想是:如果包含词条t的文档越少, IDF越大,则说明词条具有很好的类别区分能力。TDF的计算公式为:
I D F = l o g ( 语 料 库 的 文 档 总 数 包 含 词 条 w 的 文 档 数 + 1 ) IDF=log\left ( \frac{语料库的文档总数}{包含词条w的文档数+1}\right ) IDF=log(包含词条w的文档数+1语料库的文档总数)
公式中分母之所以要加1,是为了避免分母为0
这里通过对计算机领域论文的标题和摘要进行文本特征提取,并根据这些文本特征来训练多分类模型,以此来识别不同类型的论文。
# 导入所需的package
import seaborn as sns #用于画图
from bs4 import BeautifulSoup #用于爬取arxiv的数据
import re #用于正则表达式,匹配字符串的模式
import requests #用于网络连接,发送网络请求,使用域名获取对应信息
import json #读取数据,我们的数据为json格式的
import pandas as pd #数据处理,数据分析
import matplotlib.pyplot as plt #画图工具
import warnings
warnings.filterwarnings("ignore") #过滤掉警告的意思
from pyforest import *
#定义读取文本数据的函数
def readArxivFile(path, columns=['id', 'submitter', 'authors', 'title', 'comments', 'journal-ref', 'doi',
'report-no', 'categories', 'license', 'abstract', 'versions',
'update_date', 'authors_parsed'], count=None):
'''
定义读取文件的函数
path: 文件路径
columns: 需要选择的列
count: 读取行数
'''
data = []
with open(path, 'r') as f:
for idx, line in enumerate(f):
if idx == count:
break
d = json.loads(line)
d = {col : d[col] for col in columns}
data.append(d)
data = pd.DataFrame(data)
return data
data = readArxivFile('F:/data/arxiv-metadata-oai-2019.json',
['id', 'title', 'categories', 'abstract'],
200000)
#查看数据前五行
data.head()
id | title | categories | abstract | |
---|---|---|---|---|
0 | 0704.0297 | Remnant evolution after a carbon-oxygen white ... | astro-ph | We systematically explore the evolution of t... |
1 | 0704.0342 | Cofibrations in the Category of Frolicher Spac... | math.AT | Cofibrations are defined in the category of ... |
2 | 0704.0360 | Torsional oscillations of longitudinally inhom... | astro-ph | We explore the effect of an inhomogeneous ma... |
3 | 0704.0525 | On the Energy-Momentum Problem in Static Einst... | gr-qc | This paper has been removed by arXiv adminis... |
4 | 0704.0535 | The Formation of Globular Cluster Systems in M... | astro-ph | The most massive elliptical galaxies show a ... |
#将数据中的'title'列与'abstract'列进行合并,便于后续分类模型的训练
data['text'] = data['title'] + data['abstract']
data['text'] = data['text'].apply(lambda x: x.replace('\n',' '))
data['text'] = data['text'].apply(lambda x: x.lower())
data = data.drop(['abstract', 'title'], axis=1) #删除原有的列
#对数据中的多个类别和单个类别进行处理
# 多个类别,包含子分类
data['categories'] = data['categories'].apply(lambda x : x.split(' '))
# 单个类别,不包含子分类
data['categories_big'] = data['categories'].apply(lambda x : [xx.split('.')[0] for xx in x])
#对数据进行类别编码
from sklearn.preprocessing import MultiLabelBinarizer
mlb = MultiLabelBinarizer()
data_label = mlb.fit_transform(data['categories_big'].iloc[:])
data_label.shape
(170618, 34)
from sklearn.feature_extraction.text import TfidfVectorizer
vectorizer = TfidfVectorizer(max_features=4000) #提取特征,限定特征提取数量不超过4000个
vectorizer
TfidfVectorizer(analyzer=‘word’, binary=False, decode_error=‘strict’,
dtype=, encoding=‘utf-8’,
input=‘content’, lowercase=True, max_df=1.0, max_features=4000,
min_df=1, ngram_range=(1, 1), norm=‘l2’, preprocessor=None,
smooth_idf=True, stop_words=None, strip_accents=None,
sublinear_tf=False, token_pattern=’(?u)\b\w\w+\b’,
tokenizer=None, use_idf=True, vocabulary=None)
data_tfidf = vectorizer.fit_transform(data['text'].iloc[:])
# 划分训练集和验证集
from sklearn.model_selection import train_test_split
x_train, x_test, y_train, y_test = train_test_split(data_tfidf, data_label,
test_size = 0.2,random_state = 1)
# 构建多标签分类模型
#这里使用先验为多项式分布的朴素贝叶斯模型
from sklearn.multioutput import MultiOutputClassifier
from sklearn.naive_bayes import MultinomialNB
clf = MultiOutputClassifier(MultinomialNB()).fit(x_train, y_train)
clf
MultiOutputClassifier(estimator=MultinomialNB(alpha=1.0, class_prior=None,
fit_prior=True),
n_jobs=None)
#评估模型拟合效果,输出分类模型报告
from sklearn.metrics import classification_report
print(classification_report(y_test, clf.predict(x_test)))
precision recall f1-score support 0 0.00 0.00 0.00 0 1 0.00 0.00 0.00 1 2 0.00 0.00 0.00 0 3 0.91 0.85 0.88 3625 4 0.00 0.00 0.00 4 5 0.00 0.00 0.00 0 6 0.00 0.00 0.00 1 7 0.00 0.00 0.00 0 8 0.77 0.76 0.77 3801 9 0.84 0.89 0.86 10715 10 0.00 0.00 0.00 0 11 0.00 0.00 0.00 186 12 0.44 0.41 0.42 1621 13 0.00 0.00 0.00 1 14 0.75 0.59 0.66 1096 15 0.61 0.80 0.69 1078 16 0.90 0.19 0.32 242 17 0.53 0.67 0.59 1451 18 0.71 0.54 0.62 1400 19 0.88 0.84 0.86 10243 20 0.40 0.09 0.15 934 21 0.00 0.00 0.00 1 22 0.87 0.03 0.06 414 23 0.48 0.65 0.55 517 24 0.37 0.33 0.35 539 25 0.00 0.00 0.00 1 26 0.60 0.42 0.49 3891 27 0.00 0.00 0.00 0 28 0.82 0.08 0.15 676 29 0.86 0.12 0.21 297 30 0.80 0.40 0.53 1714 31 0.00 0.00 0.00 4 32 0.56 0.65 0.60 3398 33 0.00 0.00 0.00 0 micro avg 0.76 0.70 0.72 47851 macro avg 0.39 0.27 0.29 47851 weighted avg 0.75 0.70 0.71 47851 samples avg 0.74 0.76 0.72 47851
在上面文本分类模型的评估结果中,precision表示查准率,recall表示查全率,f1-score表示F1值,support表示准确分类的论文数量。从评估结果可以看出,在模型训练的33个类别中,不同类别上的准确率差异很大。平均而言,准确率有百分之七十多。