得知李航老师的《统计学习方法》出了第二版,我第一时间就买了。看了这本书的目录,非常高兴,好家伙,居然把主题模型都写了,还有pagerank。一路看到了马尔科夫蒙特卡罗方法和LDA主题模型这里,被打击到了,满满都是数学公式。LDA是目前为止我见过最复杂的模型了。

找了培训班的视频看,对LDA模型有了大致的认识。下面总结一点东西。

1、LDA与PLSA的联系

LDA模型和PLSA的联系非常紧密,都是概率模型(LSA是非概率模型),是利用概率生成模型对文本集合进行主题分析的无监督学习方法。

不同在于,PLSA是用了频率学派的方法,用极大似然估计进行学习,而LDA是用了贝叶斯学派的方法,进行贝叶斯推断,所以LDA就是在pLSA的基础上加了⻉叶斯框架,即LDA就是pLSA的⻉叶斯版本 。

LDA和PLSA都假设存在两个多项分布:话题是单词的多项分布,文本是话题的多项分布。不同在于,LDA认为多项分布的参数也服从一个分布,而不是固定不变的,使用狄利克雷分布作为多项分布的先验分布,也就是多项分布的参数服从狄利克雷分布。

为啥引入先验分布呢?因为这样能防止过拟合。为啥选择狄利克雷分布呢作为先验分布呢?因为狄利克雷分布是多项分布的共轭先验分布,那么先验分布和后验分布的形式相同,便于由先验分布得到后验分布。

2、LDA的文本集合生成过程

首先由狄立克雷分布得到话题分布的参数的分布,然后随机生成一个文本的话题分布,之后在该文本的每个位置,依据该文本的话题分布随机生成一个话题;

然后由狄利克雷分布得到单词分布的参数的分布,再得到话题的单词分布,在该位置依据该话题的单词分布随机生成一个单词,直到文本的最后一个位置,生成整个文本;

最后重复以上过程,生成所有的文本。

下面是两个小案例,用gensim训练LDA模型,进行新闻文本主题抽取,还有一个是希拉里邮件的主题抽取。

github:https://github.com/DengYangyong/LDA_gensim

一、LDA新闻文本主题抽取

第一步:对新闻进行分词

这次使用的新闻文档中有5000条新闻,有10类新闻,['体育', '财经', '房产', '家居', '教育', '科技', '时尚', '时政', '游戏', '娱乐'],每类有500条新闻。首先对文本进行清洗,去掉停用词、非汉字的特殊字符等。然后用jieba进行分词,将分词结果保存好。

#!/usr/bin/python
# -*- coding:utf-8 -*- import jieba,os,re
from gensim import corpora, models, similarities """创建停用词列表"""
def stopwordslist():
stopwords = [line.strip() for line in open('./stopwords.txt',encoding='UTF-8').readlines()]
return stopwords """对句子进行中文分词"""
def seg_depart(sentence):
sentence_depart = jieba.cut(sentence.strip())
stopwords = stopwordslist()
outstr = ''
for word in sentence_depart:
if word not in stopwords:
outstr += word
outstr += " "
# outstr:'黄蜂 湖人 首发 科比 带伤 战 保罗 加索尔 ...'
return outstr """如果文档还没分词,就进行分词"""
if not os.path.exists('./cnews.train_jieba.txt'):
# 给出文档路径
filename = "./cnews.train.txt"
outfilename = "./cnews.train_jieba.txt"
inputs = open(filename, 'r', encoding='UTF-8')
outputs = open(outfilename, 'w', encoding='UTF-8') # 把非汉字的字符全部去掉
for line in inputs:
line = line.split('\t')[1]
line = re.sub(r'[^\u4e00-\u9fa5]+','',line)
line_seg = seg_depart(line.strip())
outputs.write(line_seg.strip() + '\n') outputs.close()
inputs.close()
print("删除停用词和分词成功!!!")

第二步:构建词频矩阵,训练LDA模型

gensim所需要的输入格式为:['黄蜂', '湖人', '首发', '科比', '带伤', '战',...],也就是每篇文档是一个列表,元素为词语。

然后构建语料库,再利用语料库把每篇新闻进行数字化,corpus就是数字化后的结果。

第一条新闻ID化后的结果为corpus[0]:[(0, 1), (1, 1), (2, 1), (3, 1), (4, 1),...],每个元素是新闻中的每个词语的ID和频率。

最后训练LDA模型。LDA是一种无监督学习方法,我们可以自由选择主题的个数。这里我们做了弊,事先知道了新闻有10类,就选择10个主题吧。

LDA模型训练好之后,我们可以查看10个主题的单词分布。

第6个主题(从0开始计数)的单词分布如下。还行,从“拍摄、电影、柯达”这些词,可以大致看出是娱乐主题。

(5, '0.007*"中" + 0.004*"拍摄" + 0.004*"说" + 0.003*"英语" + 0.002*"时间" + 0.002*"柯达" + 0.002*"中国" + 0.002*"国泰" + 0.002*"市场" + 0.002*"电影"')

从第10个主题的单词分布也大致可以看出是财经主题。

(9, '0.085*"基金" + 0.016*"市场" + 0.014*"公司" + 0.013*"投资" + 0.012*"股票" + 0.011*"分红" + 0.008*"中" + 0.007*"一季度" + 0.006*"经理" + 0.006*"收益"')

但效果还是不太令人满意,因为其他的主题不太看得出来是什么。

"""准备好训练语料,整理成gensim需要的输入格式"""
fr = open('./cnews.train_jieba.txt', 'r',encoding='utf-8')
train = []
for line in fr.readlines():
line = [word.strip() for word in line.split(' ')]
train.append(line)
# train: [['黄蜂', '湖人', '首发', '科比', '带伤', '战',...],[...],...] """构建词频矩阵,训练LDA模型"""
dictionary = corpora.Dictionary(train)
# corpus[0]: [(0, 1), (1, 1), (2, 1), (3, 1), (4, 1),...]
# corpus是把每条新闻ID化后的结果,每个元素是新闻中的每个词语,在字典中的ID和频率
corpus = [dictionary.doc2bow(text) for text in train] lda = models.LdaModel(corpus=corpus, id2word=dictionary, num_topics=10)
topic_list = lda.print_topics(10)
print("10个主题的单词分布为:\n")
for topic in topic_list:
print(topic)
10个主题的单词分布为:

(0, '0.008*"中" + 0.005*"市场" + 0.004*"中国" + 0.004*"货币" + 0.004*"托管" + 0.003*"新" + 0.003*"债券" + 0.003*"说" + 0.003*"公司" + 0.003*"做"')
(1, '0.081*"基金" + 0.013*"公司" + 0.011*"投资" + 0.008*"行业" + 0.007*"中国" + 0.007*"市场" + 0.007*"中" + 0.007*"亿元" + 0.006*"规模" + 0.005*"新"')
(2, '0.013*"功能" + 0.009*"采用" + 0.008*"机身" + 0.007*"设计" + 0.007*"支持" + 0.007*"中" + 0.005*"玩家" + 0.005*"拍摄" + 0.005*"拥有" + 0.005*"倍"')
(3, '0.007*"中" + 0.006*"佣金" + 0.006*"企业" + 0.004*"考" + 0.004*"万家" + 0.003*"市场" + 0.003*"单词" + 0.003*"橱柜" + 0.003*"说" + 0.003*"行业"')
(4, '0.012*"拍摄" + 0.007*"中" + 0.007*"万" + 0.006*"镜头" + 0.005*"搭载" + 0.005*"英寸" + 0.005*"高清" + 0.005*"约" + 0.004*"拥有" + 0.004*"元"')
(5, '0.007*"中" + 0.004*"拍摄" + 0.004*"说" + 0.003*"英语" + 0.002*"时间" + 0.002*"柯达" + 0.002*"中国" + 0.002*"国泰" + 0.002*"市场" + 0.002*"电影"')
(6, '0.024*"考试" + 0.010*"相机" + 0.008*"套装" + 0.007*"拍摄" + 0.005*"万" + 0.005*"玩家" + 0.005*"中" + 0.004*"英寸" + 0.004*"索尼" + 0.004*"四级"')
(7, '0.019*"赎回" + 0.007*"基金" + 0.007*"净" + 0.006*"中" + 0.004*"市场" + 0.004*"资产" + 0.004*"收益" + 0.003*"中国" + 0.003*"债券" + 0.003*"说"')
(8, '0.010*"基金" + 0.010*"中" + 0.006*"公司" + 0.005*"产品" + 0.005*"市场" + 0.004*"元" + 0.004*"中国" + 0.004*"投资" + 0.004*"信息" + 0.004*"考试"')
(9, '0.085*"基金" + 0.016*"市场" + 0.014*"公司" + 0.013*"投资" + 0.012*"股票" + 0.011*"分红" + 0.008*"中" + 0.007*"一季度" + 0.006*"经理" + 0.006*"收益"')

第三步:抽取新闻的主题

我们还可以利用训练好的LDA,得到一条新闻的主题分布,也就是一条新闻属于各主题的可能性的概率分布。

找了三条新闻,分别是体育,娱乐和科技新闻:

体育    马晓旭意外受伤让国奥警惕 无奈大雨格外青睐殷家军记者傅亚雨沈阳报道 来到沈阳,国奥队依然没有摆脱雨水的困扰 ...

娱乐    尚雯婕筹备回沪献演□晨报记者 郭翔鹤 北京摄影报道 3月在北京举行了自己的首唱“尚佳分享·尚雯婕2008北京演唱会”后 ...

科技    摩托罗拉:GPON在FTTH中比EPON更有优势作 者:鲁义轩2009年,在国内光进铜退的火热趋势下,摩托罗拉携其在...

然后同样进行分词、ID化,通过lda.get_document_topics(corpus_test) 这个函数得到每条新闻的主题分布。得到新闻的主题分布之后,通过计算余弦距离,应该也可以进行文本相似度比较。

从结果中可以看到体育新闻的第6个主题的权重最大:(5, 0.60399055),可惜从第6个主题的单词分布来看,貌似这是个娱乐主题。

娱乐新闻的主题分布中,第5个主题的权重最大:(4, 0.46593386),而科技新闻的主题分布中,第3个主题的权重最大:(2, 0.38577113)。

"""抽取新闻的主题"""
# 用来测试的三条新闻,分别为体育、娱乐和科技新闻
file_test = "./cnews.test.txt"
news_test = open(file_test, 'r', encoding='UTF-8') test = []
# 处理成正确的输入格式
for line in news_test:
line = line.split('\t')[1]
line = re.sub(r'[^\u4e00-\u9fa5]+','',line)
line_seg = seg_depart(line.strip())
line_seg = [word.strip() for word in line_seg.split(' ')]
test.append(line_seg) # 新闻ID化
corpus_test = [dictionary.doc2bow(text) for text in test]
# 得到每条新闻的主题分布
topics_test = lda.get_document_topics(corpus_test)
labels = ['体育','娱乐','科技']
for i in range(3):
print('这条'+labels[i]+'新闻的主题分布为:\n')
print(topics_test[i],'\n') fr.close()
news_test.close()
这条体育新闻的主题分布为:

[(2, 0.022305986), (3, 0.20627314), (4, 0.039145608), (5, 0.60399055), (7, 0.1253269)] 

这条娱乐新闻的主题分布为:

[(3, 0.06871579), (4, 0.46593386), (7, 0.23081028), (8, 0.23132402)] 

这条科技新闻的主题分布为:

[(2, 0.38577113), (5, 0.14801453), (6, 0.09730849), (7, 0.36559567)] 

二、希拉里邮件门主题抽取

在美国大选期间,希拉里的邮件被泄露出来了,有6000多封邮件,我们可以用LDA主题模型对这些邮件的进行主题抽取,得到每个主题的单词分布,和每封邮件的主题分布。

还可以利用训练好模型,得到新邮件的主题分布。

步骤和以上的案例差不多,只是不需要进行分词。

第一步:用正则表达式清洗数据,并去除停用词

#!/usr/bin/python
# -*- coding:utf-8 -*- import numpy as np
import pandas as pd
import re from gensim import corpora, models, similarities
import gensim """第一步:用正则表达式清洗数据,并去除停用词"""
df = pd.read_csv("HillaryEmails.csv")
# 原邮件数据中有很多Nan的值,直接扔了。
df = df[['Id','ExtractedBodyText']].dropna() # 用正则表达式清洗数据
def clean_email_text(text):
text = text.replace('\n'," ") # 新行,我们是不需要的
text = re.sub(r"-", " ", text) # 把 "-" 的两个单词,分开。(比如:july-edu ==> july edu)
text = re.sub(r"\d+/\d+/\d+", "", text) # 日期,对主体模型没什么意义
text = re.sub(r"[0-2]?[0-9]:[0-6][0-9]", "", text) # 时间,没意义
text = re.sub(r"[\w]+@[\.\w]+", "", text) # 邮件地址,没意义
text = re.sub(r"/[a-zA-Z]*[:\//\]*[A-Za-z0-9\-_]+\.+[A-Za-z0-9\.\/%&=\?\-_]+/i", "", text) # 网址,没意义 # 以防还有其他除了单词以外的特殊字符(数字)等等,我们把特殊字符过滤掉
# 只留下字母和空格
# 再把单个字母去掉,留下单词
pure_text = ''
for letter in text:
if letter.isalpha() or letter==' ':
pure_text += letter text = ' '.join(word for word in pure_text.split() if len(word)>1)
return text docs_text = df['ExtractedBodyText']
docs = docs_text.apply(lambda s: clean_email_text(s)) # 得到所有邮件的内容
doclist = docs.values
print("一共有",len(doclist),"封邮件。\n")
print("第1封邮件未清洗前的内容为: \n",docs_text.iloc[0],'\n') # 去除停用词,处理成gensim需要的输入格式
stopwords = [word.strip() for word in open('./stopwords.txt','r').readlines()]
# 每一封邮件都有星期和月份,这里也把他们过滤掉
weeks = ['monday','mon','tuesday','tues','wednesday','wed','thursday','thur','friday','fri','saturday','sat','sunday','sun']
months = ['jan','january','feb','february','mar','march','apr','april','may','jun','june','jul',\
'july','aug','august','sept','september','oct','october','nov','november','dec','december']
stoplist = stopwords+weeks+months+['am','pm']
texts = [[word for word in doc.lower().split() if word not in stoplist] for doc in doclist] texts = [[word for word in doc.lower().split() if word not in stoplist] for doc in doclist]
print("第1封邮件去除停用词并处理成gensim需要的格式为:\n",texts[0],'\n')
一共有 6742 封邮件。

第1封邮件未清洗前的内容为:
B6
Thursday, March 3, 2011 9:45 PM
H: Latest How Syria is aiding Qaddafi and more... Sid
hrc memo syria aiding libya 030311.docx; hrc memo syria aiding libya 030311.docx
March 3, 2011
For: Hillary 第1封邮件去除停用词并处理成gensim需要的格式为:
['latest', 'syria', 'aiding', 'qaddafi', 'sid', 'hrc', 'memo', 'syria', 'aiding', 'libya', 'docx', 'hrc', 'memo', 'syria', 'aiding', 'libya', 'docx', 'hillary']

第二步:构建语料库,训练LDA模型

这个英文的stopwordlist感觉不太行,从最终得到的单词分布来看,us、would这种词居然还有。这些单词看得眼睛都花了,不容看出来主题是啥。

我们看第8个主题的单词分布,里面的词有:state,obama,president,government,估计这个主题与当前总统有关。

(7, '0.008*"us" + 0.008*"new" + 0.007*"would" + 0.005*"state" + 0.005*"obama" + 0.004*"one" + 0.004*"said" + 0.004*"president" + 0.003*"first" + 0.003*"government"'),

"""第二步:构建语料库,将文本ID化"""
dictionary = corpora.Dictionary(texts)
corpus = [dictionary.doc2bow(text) for text in texts]
# 将每一篇邮件ID化
print("第1封邮件ID化后的结果为:\n",corpus[0],'\n') """训练LDA模型"""
lda = gensim.models.ldamodel.LdaModel(corpus=corpus, id2word=dictionary, num_topics=10)# 所有主题的单词分布
print(lda.print_topics(num_topics=10, num_words=10))
第1封邮件ID化后的结果为:
[(0, 3), (1, 2), (2, 1), (3, 2), (4, 1), (5, 2), (6, 2), (7, 1), (8, 1), (9, 3)] [(0, '0.008*"us" + 0.008*"state" + 0.006*"doc" + 0.006*"afghan" + 0.005*"taliban" + 0.005*"said" + 0.003*"department" + 0.003*"strategic" + 0.003*"diplomacy" + 0.003*"afghanistan"'),
(1, '0.019*"pls" + 0.014*"call" + 0.013*"cheryl" + 0.013*"print" + 0.012*"fw" + 0.011*"mills" + 0.010*"state" + 0.010*"sullivan" + 0.009*"secretary" + 0.008*"huma"'),
(2, '0.012*"get" + 0.010*"see" + 0.009*"call" + 0.008*"good" + 0.008*"im" + 0.007*"thx" + 0.007*"know" + 0.007*"think" + 0.007*"today" + 0.007*"like"'),
(3, '0.069*"fyi" + 0.007*"sbwhoeop" + 0.006*"sid" + 0.005*"waldorf" + 0.005*"talk" + 0.004*"organizing" + 0.004*"fw" + 0.004*"abedin" + 0.004*"agree" + 0.004*"huma"'),
(4, '0.004*"ri" + 0.003*"phil" + 0.003*"yeah" + 0.003*"consulted" + 0.003*"arrange" + 0.003*"mayors" + 0.003*"cloture" + 0.003*"windows" + 0.002*"denis" + 0.002*"miliband"'),
(5, '0.007*"us" + 0.006*"people" + 0.006*"would" + 0.006*"one" + 0.006*"american" + 0.005*"israel" + 0.005*"said" + 0.004*"government" + 0.004*"united" + 0.004*"also"'),
(6, '0.012*"yes" + 0.009*"tomorrow" + 0.007*"boehner" + 0.006*"kurdistan" + 0.006*"still" + 0.005*"message" + 0.005*"talk" + 0.005*"call" + 0.004*"ops" + 0.004*"would"'),
(7, '0.008*"us" + 0.008*"new" + 0.007*"would" + 0.005*"state" + 0.005*"obama" + 0.004*"one" + 0.004*"said" + 0.004*"president" + 0.003*"first" + 0.003*"government"'),
(8, '0.008*"president" + 0.008*"obama" + 0.007*"said" + 0.006*"white" + 0.005*"house" + 0.005*"state" + 0.005*"percent" + 0.005*"ok" + 0.005*"new" + 0.005*"one"'),
(9, '0.024*"office" + 0.017*"secretarys" + 0.013*"meeting" + 0.012*"room" + 0.009*"state" + 0.009*"time" + 0.008*"department" + 0.008*"call" + 0.007*"treaty" + 0.007*"arrive"')]

第三步:查看邮件的主题分布

查看了第一封邮件的主题分布,然后推测了希拉里两条推特的主题。

"""第三步:查看某封邮件所属的主题"""
print("第1封邮件的大致内容为:\n",texts[0],'\n')
topic = lda.get_document_topics(corpus[0])
print("第1封邮件的主题分布为:\n",topic,'\n') # 希拉里发的两条推特
# 给大伙翻译一下这两句:
# 这是选举的一天!数以百万计的美国人投了希拉里的票。加入他们吧,确定你投给谁。
# 希望今天每个人都能度过一个安乐的感恩节,和家人朋友共度美好时光——来自希拉里的问候。 twitter = ["It's Election Day! Millions of Americans have cast their votes for Hillary—join them and confirm where you vote ",
"Hoping everyone has a safe & Happy Thanksgiving today, & quality time with family & friends. -H"] text_twitter = [clean_email_text(s) for s in twitter]
text_twitter = [[word for word in text.lower().split() if word not in stoplist] for text in text_twitter]
corpus_twitter = [dictionary.doc2bow(text) for text in text_twitter]
topics_twitter = lda.get_document_topics(corpus_twitter)
print("这两条推特的主题分布分别为:\n",topics_twitter[0] ,'\n',topics_twitter[1])
第1封邮件的大致内容为:
['latest', 'syria', 'aiding', 'qaddafi', 'sid', 'hrc', 'memo', 'syria', 'aiding', 'libya', 'docx', 'hrc', 'memo', 'syria', 'aiding', 'libya', 'docx', 'hillary'] 第1封邮件的主题分布为:
[(7, 0.9499477)] 这两条推特的主题分布分别为:
[(0, 0.0111170085), (1, 0.011118207), (2, 0.01111913), (3, 0.011116115), (4, 0.89994085), (5, 0.011116263), (6, 0.011116605), (7, 0.011117295), (8, 0.01111973), (9, 0.0111187985)]
[(4, 0.9181052)]

参考资料:

1、李航:《统计学习方法》(第二版)

2、某培训班资料

文本主题抽取:用gensim训练LDA模型的更多相关文章

  1. 文本主题模型之LDA(二) LDA求解之Gibbs采样算法

    文本主题模型之LDA(一) LDA基础 文本主题模型之LDA(二) LDA求解之Gibbs采样算法 文本主题模型之LDA(三) LDA求解之变分推断EM算法(TODO) 本文是LDA主题模型的第二篇, ...

  2. 文本主题模型之LDA(一) LDA基础

    文本主题模型之LDA(一) LDA基础 文本主题模型之LDA(二) LDA求解之Gibbs采样算法 文本主题模型之LDA(三) LDA求解之变分推断EM算法(TODO) 在前面我们讲到了基于矩阵分解的 ...

  3. python应用:主题分类(gensim lda)

    安装第三方包:gensim 首先,执行去停词操作(去除与主题无关的词) #-*-coding:utf8-*- import jieba def stopwordslist(filepath): sto ...

  4. 大佬整理出来的干货:LDA模型实现—Python文本挖掘

    前言 本文的文字及图片来源于网络,仅供学习.交流使用,不具有任何商业用途,版权归原作者所有,如有问题请及时联系我们以作处理. PS:如有需要Python学习资料的小伙伴可以加点击下方链接自行获取htt ...

  5. 文本主题模型之LDA(三) LDA求解之变分推断EM算法

    文本主题模型之LDA(一) LDA基础 文本主题模型之LDA(二) LDA求解之Gibbs采样算法 文本主题模型之LDA(三) LDA求解之变分推断EM算法 本文是LDA主题模型的第三篇,读这一篇之前 ...

  6. gensim LDA模型提取每篇文档所属主题(概率最大主题所在)

    gensim的LDA算法中很容易提取到每篇文章的主题分布矩阵,但是一般地还需要进一步获取每篇文章归属到哪个主题概率最大的数据,这个在检索gensim文档和网络有关文章后,发现竟然没有. 简单写了一下. ...

  7. 文本分布式表示(三):用gensim训练word2vec词向量

    今天参考网上的博客,用gensim训练了word2vec词向量.训练的语料是著名科幻小说<三体>,这部小说我一直没有看,所以这次拿来折腾一下. <三体>这本小说里有不少人名和一 ...

  8. 文本主题模型之非负矩阵分解(NMF)

    在文本主题模型之潜在语义索引(LSI)中,我们讲到LSI主题模型使用了奇异值分解,面临着高维度计算量太大的问题.这里我们就介绍另一种基于矩阵分解的主题模型:非负矩阵分解(NMF),它同样使用了矩阵分解 ...

  9. 文本主题模型之潜在语义索引(LSI)

    在文本挖掘中,主题模型是比较特殊的一块,它的思想不同于我们常用的机器学习算法,因此这里我们需要专门来总结文本主题模型的算法.本文关注于潜在语义索引算法(LSI)的原理. 1. 文本主题模型的问题特点 ...

随机推荐

  1. 我的Java开发学习之旅------>使用Working Setst将Eclipse中的项目分类使项目一目了然

    今天发现Eclipse中若有太多的项目,杂七杂八的,看起来会非常的痛苦.今天请教公司的前辈学会了一个方法,在Eclipse中,当项目比较多的时候,我们可以用WorkingSet将这些项目分类,把相关连 ...

  2. linux日志系统介绍 —— syslog(),openlog(),closelog()

    函数使用介绍 这里面的三个函数openlog, syslog.closelog是一套系统日志写入接口.另外那个vsyslog和syslog功能一样,仅仅是參数格式不同.         通常.sysl ...

  3. indows下PHP通过ffmpeg给上传的视频截图详解

    windows下PHP通过ffmpeg给上传的视频截图详解,php_ffmpeg.dll安装下载,找了很久php_ffmpeg.dll的下载地址和应用,发现有用的资源很少,现在问题解决了,贴出来跟大家 ...

  4. sql性能分析语句

    SELECT creation_time N'语句编译时间' ,last_execution_time N'上次执行时间' ,total_physical_reads N'物理读取总次数' ,tota ...

  5. Automator 实例:使用快捷键 实现 快速在当前路径 打开 iTerm

    1. 在 finder -> 应用程序 或 通过 Spotlight 打开:Automator.app 2. 选择新建 “服务” 3. 设置服务,见下图,设置完成之后,command + s 保 ...

  6. SPOJ - PHRASES Relevant Phrases of Annihilation —— 后缀数组 出现于所有字符串中两次且不重叠的最长公共子串

    题目链接:https://vjudge.net/problem/SPOJ-PHRASES PHRASES - Relevant Phrases of Annihilation no tags  You ...

  7. win7 jdk1.7配置环境变量

    1.安装目录,C:\Program Files\Java

  8. P2060 [HNOI2006]马步距离

    P2060 [HNOI2006]马步距离 数据到百万级别,明显爆搜不行,剪枝也没法剪.先打表.发现小数据内步数比较受位置关系影响,但数据一大就不影响了.大概搜了一个20*20的表把赋值语句打出来.判断 ...

  9. 微信小程序之tab切换

    .wxml <view class="select_box"> <scroll-view scroll-x="true" style=&quo ...

  10. BZOJ3674:可持久化并查集加强版

    浅谈主席树:https://www.cnblogs.com/AKMer/p/9956734.html 题目传送门:https://www.lydsy.com/JudgeOnline/problem.p ...