全栈工程师开发手册 (作者:栾鹏)
其中使用到了urllib、BeautifulSoup爬虫和结巴中文分词的相关知识。
调试环境python3.6
# 根据连接爬取中文网站,获取标题、子连接、子连接数目、连接描述、中文分词列表,
import urllib
from bs4 import BeautifulSoup
import bs4
import jieba #对中文进行分词
# 分词时忽略下列词
ignorewords=[',','。','?','“','”','!',';',':','\n','、','-',',','.','?','\r\n','_',' ']
# 定义爬虫类。获取链接的题目、描述、分词、深度
class crawler:
def __init__(self,url):
self.url = url
self.urls={}
self.urls[url]={
'num':1, #连接被引用的次数
'title':'', #连接的标题
'text':'', #连接的描述
'allword':[], #连接的所有分词列表
}
def getword(self,soup):
# 获取每个单词
text=self.gettextonly(soup) #提取所有显示出来的文本
words=self.separatewords(text) #使用分词器进行分词
allword=[]
for word in words:
if word not in ignorewords:
allword.append(word)
# print(allword)
return allword
# 根据一个网页源代码提取文字(不带标签的)。由外至内获取文本元素。style和script内不要
def gettextonly(self,soup):
v=soup.string
if v==None:
c=soup.contents # 直接子节点的列表,将<tag>所有儿子节点存入列表
resulttext=''
for t in c:
if t.name=='style' or t.name=='script': #当元素为style和script和None时不获取内容
continue
subtext=self.gettextonly(t)
resulttext+=subtext+'\n'
return resulttext
else:
if isinstance(v,bs4.element.Comment): #代码中的注释不获取
return ''
return v.strip()
# 利用正则表达式提取单词(不能区分中文)。会将任何非字母非数字字符看做分隔符
def separatewords(self,text):
seg_list = jieba.cut(text, cut_all=False) #使用结巴进行中文分词
return seg_list
# splitter=re.compile('\\W*')
# return [s.lower() for s in splitter.split(text) if s!='']
#爬虫主函数
def crawl(self):
try:
response=urllib.request.urlopen(self.url)
except:
print("Could not open %s" % self.url)
return
try:
text = str(response.read(),encoding='utf-8')
soup=BeautifulSoup(text,'html.parser')
title = soup.title
self.urls[self.url]['title'] = title.get_text() # 将标题加入到属性中
links=soup('a')
for link in links:
if ('href' in dict(link.attrs)):
newurl=urllib.parse.urljoin(self.url,link['href'])
if newurl.find("'")!=-1: continue
newurl=newurl.split('#')[0] # 去掉位置部分
if newurl[0:4]=='http':
if newurl not in self.urls:
linkText = self.gettextonly(link) #获取连接的描述
self.urls[newurl]={
'num':1, #连接被引用的次数
'text':linkText #链接描述
}
else:
self.urls[newurl]['num']+=1 #连接数+1,这里有算法只算一次
allword = self.getword(soup.body) # 获取分词
self.urls[self.url]['allword'] = allword # 将分词加入到属性中
except:
print("Could not parse page %s" % self.url)
if __name__ == '__main__':
url='http://blog.csdn.net/luanpeng825485697/article/details/78378653'
mycrawler = crawler(url)
mycrawler.crawl()
print(mycrawler.urls[url]['allword'])