知识图谱

知识图谱

知识图谱定义

知识图谱的定义:

知识图谱的具体:

知识图谱相关领域

整体概况:

CQL语句

1
2


1
2


1
2


1
2


生物信息学

生物信息学概述

所需资料

1
2
3
1.视频:
山东大学生物信息学:https://www.bilibili.com/video/BV13t411372E/?spm_id_from=333.999.0.0
2.百度网盘(课件):https://pan.baidu.com/s/1WyBpOO2hs3qRJc7yipJW1A 提取码: 6esr

生物信息学研究对象

生物数据库分类

文献数据库(PubMed)

1
1.地址:https://pubmed.ncbi.nlm.nih.gov/

一级核酸数据库(GeneBank)

原核生物(大肠杆菌)dUTPase的NDA序列信息(X01714)

详细介绍1

详细介绍2

详细介绍3

1
2
3
1.浏览地址:https://www.ncbi.nlm.nih.gov/nuccore/X01714
2.详细介绍:如图所示
3.核酸序列: 页面GenBank:X01714.1下面有一行 FASTA(文本形式) Graphics(图形可视化)

真核生物(人)dUTPase的成熟mRNA的序列信息(U90223)

详细介绍

1
2
3
1.浏览地址:https://www.ncbi.nlm.nih.gov/nuccore/U90223
2.详细介绍:如图所示
3.核酸序列: 页面GenBank:X01714.1下面有一行 FASTA(文本形式) Graphics(图形可视化)

真核生物(人)dUTPase的DNA的序列信息(AH005568)

详细介绍

1
2
3
1.浏览地址:https://www.ncbi.nlm.nih.gov/nuccore/AH005568
2.详细介绍:如图所示
3.核酸序列: 页面GenBank:X01714.1下面有一行 FASTA(文本形式) Graphics(图形可视化)

一级核酸数据库(基因组数据库)

人基因组数据库(Ensemble)

1
2
3
4
5
1.地址:https://asia.ensembl.org/Homo_sapiens/Location/Genome
2.详细选择: 左下角图标human点击进入
3.知识点:
3.1 人的基因组有33亿个碱基分布在23个染色体上
3.2 目前已经获得人的全基因组序列

微生物宏基因组数据库(JCVI)

1
1.地址:https://www.jcvi.org/

二级核酸数据库

1
2
3
4
5
1.RefSeq数据库(参考序列数据库):通过自动及人工精选出的非冗余数据库[基因组序列、转录序列、蛋白质序列]
2.dbEST数据库(表达序列数据库):来源于不同物种的表达序列标签(EST)
3.Gene数据库:为用户提供基因序列注释和检索服务
4.ncRNAdb(非编码RNA数据库):提供非编码RNA的序列和功能信息(99种细菌、古细菌、真核生物的3万多条序列)
5.miRBase:主要存放已发表的microRNA序列和注释(可以分析microRNA在基因组中的定位和挖掘microRNA序列间的关系)

一级蛋白质序列数据库(UniProt)

三大数据库:

三大数据库合并:

UniProt解读

  1. 查找并搜索蛋白质数据库

  1. 点击第一条P33316查看内部情况

一级蛋白质结构数据库(PDB)

蛋白质的结构

PDB解读

  1. PDB网页搜索苏教授的duTPase蛋白质

  1. 浏览基本信息(点击Download Files–>PDB format)

  1. 基本信息-第一部分(基本信息部分)

  1. 基本信息-第二部分(一级结构信息部分)

  1. 基本信息-第三部分(二级结构信息部分)

  1. 基本信息-实验参数部分

  1. 基本信息-3D坐标部分

二级蛋白质数据库

二级蛋白质数据库分类

  1. CATH数据库

  1. SCOP2数据库

1
2
3
1.Pfam数据库:蛋白质结构域家族的集合
2.CATH数据库:数据库四种结构分类层次的首字母(结构域)
3.SCOP2数据库:详细描述蛋白质在结构、进化事件、功能类型三个方面的关系(将SCOP中仅基蛋白质的树状等级分类系统发展成为单向非循环网状分类系统)

专用数据库

KEGG

1
2
1.京都基因与基因组百科全书:关于基因、蛋白质、生化反应、通路的综合生物信息数据库(多个字库构成)
2.分类:KEGG下有很多分类

OMIM

1
2
1.人类孟德尔遗传文献:为临床医生和科研人员提供了关于遗传病相关技术
2.地址:https://www.ncbi.nlm.nih.gov/omim

序列

序列概念

1
2
1.蛋白质序列:由20个不同的字母(氨基酸)排列组合而成
2.核酸序列:由4个不同的字母(碱基)排列组合而成 --> DNA序列和RNA序列

序列相似性(序列一致度/序列相似度)

1
2
1.序列一致度:两个序列长度相同,那么他们一致度的定义为他们对应位置上相同的残基的数目/总长度的百分比
2.序列相似度:两个序列长度相同,那么他们相似度的定义为他们对应位置上相同+相似残基的数目/总长度的百分比

替换记分矩阵(反映残基两两相似的量化关系)

1
2
3
4
5
6
7
8
9
10
11
1.DNA替换记分矩阵:
1.1 等价矩阵
1.2 转换-颠换矩阵
1.3 BLAST矩阵

2.蛋白质替换记分矩阵:
2.1 等价矩阵
2.2 PAM矩阵
2.3 BLOSUM矩阵
2.4 遗传密码矩阵
2.5 疏水矩阵

序列比对

1
2
3
4
1.打点法
2.序列比对法
2.1 双序列全局比对法:Needleman-Wunsch算法
2.2 双序列局部比对法:Smith-Waterman算法

双序列全局比对法(Needleman-Wunsch算法)

双序列局部比对法(Smith-Waterman算法)

保守区域

系统发生树

基于距离的UPGMA法

1
2
1.根据序列两两间的距离的远近构建系统发生树
2.根据一步步合成新的矩阵(A-->AB-->CD-->ABCD)然后得到最终的系统发生树

综述提炼

参考方向

1
2
3
1.分析:偏向生物更多,需要从生物信息本质去挖掘和预测
2.算法:偏向计算机更多,需要代码能力更强(前景更大)
3.模型:用深度学习跑(DNN/RNN/CNN/MNN)

深度学习在生物信息学的应用

组学

1
2
3
4
1.蛋白质结构
2.基因表达调控
3.蛋白质分类
4.异常分类

成像

###

动手学深度学习

预备知识

数据操作

数据操作实现

读取和存储数据

1
2
3
4
5
6
7
8
9
10
11
12
13
import torch
#随意0-12
x=torch.arange(12) #使用arange创建一个行向量x
print(x)
print(x.shape) #根据张量的shape属性来访问张量的形状
print(x.numel()) #获取张量中元素的总数(形状的所有元素乘积,检查它的大小)
print(x.reshape(3,4)) #改变张量的形状 但是不改变元素数量和元素值 # x.reshape(-1,4) / x.reshape(3,-1) 通过-1来调用此自动计算出维度的功能
#全0
print(torch.zeros(2,3,4))
#全1
print(torch.ones(2,3,4))
#正态分布(均值0,标准差1)
print(torch.randn(3,4))

运算符

1
2
3
4
5
6
7
8
9
import torch
#进行四则运算
x = torch.tensor([1.0, 2, 4, 8])
y = torch.tensor([2, 2, 2, 2])
print(x+y)
print(x-y)
print(x*y)
print(x/y)
print(x**y)

广播机制

1
2
3
4
5
6
7
8
9
10
11
12
#1.通过适当复制元素来扩展一个或两个数组,以便在转换之后,两个张量具有相同的形状。 
#2.对生成的数组执行按元素操作。

import torch
a = torch.arange(3).reshape((3, 1)) # 3*1矩阵
b = torch.arange(2).reshape((1, 2)) # 1*2矩阵
print(a)
print(b)
#如果a+b的话因为两个形状不匹配 --> 广播成更大的3*2矩阵
#a将复制列
#b将赋值行
print(a+b)

索引和切片

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
import torch
x=torch.arange(12).reshape((3, 4))
print(x)

#输出最后一个元素
print(x[-1])
#输出第二个和第三个元素
print(x[1:3]) #下标第一行和第二行

#指定索引写入一个
x[1,2]=9 #第二行第三个元素改为9
print(x)
#指定索引写入很多
x[0:2,:]=111 #第一行和第二行的所有列都改为111
print(x)

节省内存(创建一样大的0矩阵)

1
2
3
4
5
6
7
8
9
10
11
12
13
import torch
#原来的问题!!
Y=torch.arange(12).reshape((3,4))
X=torch.arange(12).reshape((3,4))
before=id(Y)
Y=Y+X
print(id(Y)==before) #Y被赋值新的内存,执行内存中新位置

#原地更新
Z=torch.zeros_like(Y) #创建一个和Y一样大的
print(id(Z))
Z[:]=X+Y
print(id(Z))

深度学习框架定义的张量->Numpy张量(ndarray)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
import torch
import numpy as np
X = torch.arange(12, dtype=torch.float32).reshape((3,4))
A=X.numpy()
B=torch.tensor(A)
print(type(A)) #ndarray数组
print(type(B)) #tensor向量

#调用item函数/Python内置函数
a=torch.tensor([3.5])
print(a)
print(a.item()) #调用item函数!!转变为ndarray数组
print(float(a))
print(int(a))

数据预处理(Pandas)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34

import torch
import numpy as np
import pandas as pd
import os
#1.读取数据集
os.makedirs(os.path.join('..', 'data'), exist_ok=True)
data_file = os.path.join('..', 'data', 'house_tiny.csv') #创建 ../data/house_tiny.csv文件
with open(data_file, 'w') as f:
f.write('NumRooms,Alley,Price\n') # 列名
f.write('NA,Pave,127500\n') # 每行表示一个数据样本
f.write('2,NA,106000\n')
f.write('4,NA,178100\n')
f.write('NA,NA,140000\n')
data=pd.read_csv(data_file)
print(data)
print()

#2.处理缺失值(插值法和删除法)
inputs=data.iloc[:,0:2] #利用位置索引iloc --> data前两列为inputs data最后一列为outputs
outputs=data.iloc[:,2]
inputs=inputs.fillna(inputs.mean()) #利用均值填充
print(inputs)
print()

##对于inputs中的类别值/离散值
##Alley里面有Pava和NaN两种类型 --> pandas可以自动将此列分为两列(Alley_Pave[设置1]和Alley_nan[设置0]) 缺少的行会将“Alley_Pave”和“Alley_nan”分别设置为0和1
inputs=pd.get_dummies(inputs,dummy_na=True)
print(inputs)

#3.转换为张量格式(数值类型-->张量类型) torch.tensor()函数
X, y = torch.tensor(inputs.values), torch.tensor(outputs.values)
print(X)
print(y)

线性代数

标量/向量/矩阵/张量

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37

import torch
import numpy as np
import pandas as pd
import os

#1.标量
x=torch.tensor(3.0)
y=torch.tensor(2.0)
print("x+y:",x+y)
print("x-y:",x-y)
print("x*y:",x*y)
print("x/y:",x/y)
print("x**y:",x**y)
print()

#2.向量([标量值1,标量值2,...,标量值N]) 一阶张量
x=torch.arange(4)
print("x:",x)
print()

#3.矩阵([向量1,向量2]) 二阶张量
A=torch.arange(20).reshape(5,4) #5行4列
print("A:",A) #输出A矩阵
print("A的转置:",A.T) #输出转置
##两个形状相同的矩阵相加
A=torch.arange(20, dtype=torch.float32).reshape(5, 4)
B=A.clone()
print("A:",A)
print("A+B:",A+B)
print()

#4.张量(大写字母)
##处理图像 -->n维数组[高度轴(Red红色)/宽度轴(Green绿色)/通道轴(Blue蓝色)]
X=torch.arange(24).reshape(2,3,4)
print("X:",X)
print()

降维

降维求和

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33

import torch
import numpy as np
import pandas as pd
import os

x=torch.arange(4,dtype=torch.float32) # 0 1 2 3
print("x:",x)
print("x的总和:",x.sum())
print()

A=torch.arange(20, dtype=torch.float32).reshape(5, 4)
print("A:",A)
print("A的形状:",A.shape)
print("A的总和:",A.sum())
print()

#降维
##每列相加(↑)
A_sum_axis0=A.sum(axis=0) #按照轴0(第一行)将每列往上加到第一个位置[x1,x2,x3,x4]
print("A按照轴0:",A_sum_axis0)
print("A按照轴0的形状:",A_sum_axis0.shape)
print()
##每行相加(←)
A_sum_axis1=A.sum(axis=1) #按照轴1(第一列)将每行往左加到第一个位置[x1,x2,x3,x4]
print("A按照轴1:",A_sum_axis1)
print("A按照轴1的形状:",A_sum_axis1.shape)
print()
##行和列求和
A_sum_axis01=A.sum(axis=[0,1]) #按照轴1(第一列)将每行往左加到第一个位置[x1,x2,x3,x4]
print("A按照轴01:",A_sum_axis01)
print("A按照轴01的形状:",A_sum_axis01.shape)
print()

非降维求和(设置keepdims=True)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18

import torch
import numpy as np
import pandas as pd
import os

A=torch.arange(20, dtype=torch.float32).reshape(5, 4)
print("A:",A)
print("A的形状:",A.shape)
print("A的总和:",A.sum())
print()

#非降维求和
sum_A=A.sum(axis=1,keepdims=True) #每行计算往最左边推(行有几个就有几个元素)
print(sum_A)

#沿着某个轴计算A元素的累计总和 --cumsum函数
print(A.cumsum(axis=0)) #第一行=第一行 第二行=第二行+第一行 第三行=第一行+第二行+第三行 ...

点积(dot)

1
2
3
4
5
6
7
8
9
10
11

import torch
import numpy as np
import pandas as pd
import os

x=torch.arange(4,dtype=torch.float32)
y=torch.ones(4,dtype=torch.float32)
print("x:",x)
print("x:",y)
print(torch.dot(x,y)) # 0*0+1*1+2*1+3*1=6

矩阵-向量积(mv)

1
2
3
4
5
6
7
8
9
10
11

import torch
import numpy as np
import pandas as pd
import os

x=torch.arange(4)
A=torch.arange(20).reshape(5,4)
print(x)
print(A)
print(torch.mv(A,x))

矩阵-矩阵乘法(mm)

1
2
3
4
5
6
7
8
9
10
11

import torch
import numpy as np
import pandas as pd
import os

A=torch.arange(20).reshape(5,4)
B=torch.arange(20).reshape(4,5)
print(A)
print(B)
print(torch.mm(A,B))

范数

1
2
3
4
5
6
7
8
9
10
11
12
13

import torch
import numpy as np
import pandas as pd
import os

# L2范数(欧几里得距离)
u=torch.tensor([3.0,-4.0])
print(torch.norm(u))

# L1范数(向量元素的绝对值之和)
print(torch.abs(u).sum()) # 3.0+4.0=7.0
print(torch.norm(torch.ones(4,9)))

微积分

导数

1
2
1.概念:
2.定义:

爬虫基础

了解网页结构

1
2
3
4
5
6
7
1.网页构成:
1.1 html
1.2 css
1.3 JavaScript
2.html介绍:
2.1 header部分:看到网页的元信息(比如像title标题)
2.2 body部分:可以看到网页的内容(p/a/h1等标签)

用到的网页html代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16

<!DOCTYPE html>
<html lang="cn">
<head>
<meta charset="UTF-8">
<title>Scraping tutorial 1 | 莫烦Python</title>
<link rel="icon" href="https://morvanzhou.github.io/static/img/description/tab_icon.png">
</head>
<body>
<h1>爬虫测试1</h1>
<p>
这是一个在 <a href="https://morvanzhou.github.io/">莫烦Python</a>
<a href="https://morvanzhou.github.io/tutorials/data-manipulation/scraping/">爬虫教程</a> 中的简单测试.
</p>
</body>
</html>

匹配网页内容(两种方式)

正则表达式(regex库)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
from urllib.request import urlopen #python自带的打开
import re #正则表达式RegEx进行文字匹配
html=urlopen("https://morvanzhou.github.io/static/scraping/basic-structure.html").read().decode('utf-8')
print(html)

#1.初级页面匹配用正则表达式
##1.1 找到网页的title
res=re.findall(r"<title>(.+?)</title>",html)
print("\n文章的标题是: ",res[0])
##1.2 找到中间段落p
res=re.findall(r"<p>(.*?)</p>",html,flags=re.DOTALL) #re.DOTALL对这些tab new line不敏感
print("\n文章的中间段落是: ",res[0])
##1.3 找到所有的链接
res=re.findall(r'href="(.*?)"',html)
print("\n所有的链接:",res)

BeautifulSoup(bs4库的BeautifulSoup)

1
2
1.概念:是一个可以从HTML/XML文件中提取数据的Python库.它能够通过你喜欢的转换器实现惯用的文档导航,查找,修改文档的方式.Beautiful Soup会帮你节省数小时甚至数天的工作时间.
2.官网:https://www.crummy.com/software/BeautifulSoup/bs4/doc.zh/

解析网页:基础(按照标签名进行匹配)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
#和刚才正则表达式对比:
from urllib.request import urlopen #python自带的打开
from bs4 import BeautifulSoup #bs4里面的
html=urlopen("https://morvanzhou.github.io/static/scraping/basic-structure.html").read().decode('utf-8')
#print(html)
#2.高级页面匹配用BeautifulSoup
soup=BeautifulSoup(html,features='lxml') #将刚才获取的地址 --> lxml格式保存
#输出soup的h标题
print(soup.h1)
#输出soup的p标签
print(soup.p)
#输出soup的a标签(特别多的话可以用find_all()找到所有选项)
all_href=soup.find_all('a') #将所有a找到 -- 但是里面会有很多其他杂质(<a href="xxx">爬虫教程</a>])
print(all_href)
for i in all_href:
print("a里面的地址:",i['href'])

解析网页:CSS(按照css的class进行匹配)

要准备的html网页:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
from urllib.request import urlopen #python自带的打开
import re #正则表达式RegEx进行文字匹配
from bs4 import BeautifulSoup #bs4里面的
html=urlopen("https://mofanpy.com/static/scraping/list.html").read().decode('utf-8')
#print(html)
soup=BeautifulSoup(html,features='lxml')

#1.找到所有class=month的信息
month=soup.find_all('li',{"class":"month"}) #根据li标签获取class=month的信息
for m in month:
print(m.get_text()) #获取li标签里面的所有文字标题

#2.找到class=jan的信息 然后在ul下面继续找ul内部的li信息(一层层嵌套)
jan=soup.find('ul',{"class":'jan'})
d_jan=jan.find_all('li')
for d in d_jan:
print(d.get_text())

解析网页:正则表达式

1
2
3
4
5
6
7
8
9
10
11
12
13
from urllib.request import urlopen #python自带的打开
import re #正则表达式RegEx进行文字匹配
from bs4 import BeautifulSoup #bs4里面的

#获取网址
html=urlopen("https://mofanpy.com/static/scraping/table.html").read().decode('utf-8')
#将页面保存到soup
soup=BeautifulSoup(html,features='lxml')
#获取所有的图片 后缀是jpg的图片()
img_links=soup.find_all("img",{"src":re.compile('.*?\.jpg')}) # .匹配任何字符 *匹配前一个字符0/无限次 ?前面的字符可有可无 \.就是匹配. --> xxx.jpg
#for循环遍历
for link in img_links:
print(link['src']) #根据src进行遍历

正则表达式

正则表达式匹配流程:

1
2
3
4
5
6
7
8
9
10
11

import re #正则表达式RegEx进行文字匹配
pattern1 = "cat"
pattern2 = "bird"
string = "dog runs to cat"
#使用普通字符串匹配
print(pattern1 in string) # True
print(pattern2 in string) # False
#使用正则表达式匹配
print(re.search(pattern1,string)) #匹配到了会说范围span和匹配的内容match
print(re.search(pattern2,string)) #没匹配到就是None

灵活匹配(pattern)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
import re  #正则表达式RegEx进行文字匹配

pattern1 = "cat"
pattern2 = "bird"
string = "dog runs to cat"

#r"xxx"表示这是正则表达式
##1.r[au]n --> 匹配 ran/run
ptn=r"r[au]n"
print(re.search(ptn,string))
##2.r[A-Z]n --> 匹配rAn/rBn.../rZn
print(re.search(r"r[A-Z]n",string))
##3.r[a-z]n --> 匹配ran/rbn.../rzn
print(re.search(r"r[a-z]n",string))
##4.r[0-9]n --> 匹配r0n/r1n.../r9n
print(re.search(r"r[0-9]n]",string))
##5.r[0-9a-z] --> 匹配可以是数字也可以是任何字母
print(re.search(r"r[0-9a-z]n",string))

类型匹配(好多设定好的)

特殊的匹配类型:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
import re  #正则表达式RegEx进行文字匹配

#匹配r(任何数字)n
print(re.search(r"r\dn","run r4n")) #匹配到r4n
#匹配r(不是数字)n
print(re.search(r"r\Dn","run r4n")) #匹配到run
#匹配r(任何white space)n --比如\t \n \r \f \v
print(re.search(r"r\sn", "r\nn r4n")) #匹配到r\nn
#匹配r(不是white space)n
print(re.search(r"r\Sn", "r\nn r4n")) #匹配到r4n
#匹配r(任何大小写字母和数字还有_ a-zA-Z0-9)
print(re.search(r"r\wn", "r\nn r4n")) #匹配到r4n
#匹配r(任何不是大小写字母和数字还有_ a-zA-Z0-9这个范围内)
print(re.search(r"r\Wn", "r\nn r4n")) #匹配到r\nn
#匹配r(只在某个字的开头/结尾的空白字符)n
print(re.search(r"r\bn", "dog runs to cat")) #什么都匹配不到
#匹配(不在某个字的开头/结尾的空白字符) runs (不在某个字的开头/结尾的空白字符)
print(re.search(r"\B runs \B", "dog runs to cat")) #匹配到 runs
#匹配runs(\)
print(re.search(r"runs\\", "runs\ to me")) #匹配到runs\\
#匹配r(任何字符 除了\n)n
print(re.search(r"r.n", "r[ns to me")) #匹配r[n
#匹配(开头)dog
print(re.search(r"^dog", "dog runs to cat")) #匹配dog
#匹配cat(结尾)
print(re.search(r"cat$", "dog runs to cat")) #匹配cat
#匹配Mon(day)可有可无 -->Monday和Mon都可以
print(re.search(r"Mon(day)?", "Monday")) #匹配Monday
print(re.search(r"Mon(day)?", "Mon")) #匹配Mon

#匹配多行字符串
#使用^形式匹配行开头的字符
string="""
dog runs to cat.
I run to dog.
"""
#匹配不到
print(re.search(r"^I",string))
#可以匹配到
#可以对每一行单独处理 flags=re.M / flags=re.MULTILINE
print(re.search(r"^I",string,flags=re.M))

重复匹配(重复出现)

重复匹配分类:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
import re  #正则表达式RegEx进行文字匹配

# *重复0次/多次
print(re.search(r"ab*","a")) # a出现一次 b出现0次/多次 a
print(re.search(r"ab*","abbbbb")) # a出现一次 b出现0次/多次 abbbbb
print(re.search(r"ab*","abababab")) # a出现一次 b出现0次/多次 ab
print()

# +重复1次/多次
print(re.search(r"ab+","a")) # a出现一次 b出现一次/多次 None
print(re.search(r"ab+","ab")) #a出现一次 b出现一次/多次 ab
print(re.search(r"ab+","abb")) #a出现一次 b出现一次/多次 abb
print()

# {n,m}重复n至m次
print(re.search(r"ab{2,10}","a")) #a出现一次 b出现2-10次 None
print(re.search(r"ab{2,10}","ab")) #a出现一次 b出现2-10次 None
print(re.search(r"ab{2,10}","abb")) #a出现一次 b出现2-10次 abb
print(re.search(r"ab{2,10}","abbbb")) #a出现一次 b出现2-10次 abbbb
print(re.search(r"ab{2,10}","ababab")) #a出现一次 b出现2-10次 None

分组(re.search().group())

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
import re  #正则表达式RegEx进行文字匹配

# match.group()表示返回所有组里的内容
string="ID: 021523, Date: Feb/12/2017"
match=re.search(r"(\d+), Date:(.+)",string) # (\d+)表示匹配数字重复1次或者多次 (.+)表示匹配任何字符(除了\n)
print(match.group()) #匹配出来 021526, Date:Feb/12/2017
print(match.group(1)) # 021526
print(match.group(2)) # Feb/12/2017
print()

# ?P<名字>
string= "ID: 021523, Date: Feb/12/2017"
match=re.search(r"(?P<id>\d+), Date:(?P<date>.+)",string) #匹配出来 id:021526 date:Date:Feb/12/2017
print(match.group('id')) # 021523
print(match.group('date')) # Date: Feb/12/2017

findall(全部)和or(|)

1
2
3
4
5
6
import re  #正则表达式RegEx进行文字匹配

#findall是找到所有的可能
#|是找到其中一个(要么是前者要么是后者)
print(re.findall(r"r[uae]n","run ran ren")) # ['run', 'ran', 'ren']
print(re.findall(r"(run|ran)","run ran ren")) # ['run', 'ran']

replace(re.sub())

1
2
3
4
5
import re  #正则表达式RegEx进行文字匹配

#re.sub()替换
#匹配rans|runs
print(re.sub(r"r[au]ns", "catches", "dog runs to cat")) #用catches替换掉runs/rans

split(re.split())

1
2
3
4
5
import re  #正则表达式RegEx进行文字匹配

#re.split()
string="a;b,c.d;]we"
print(re.split(r"[,;\.]",string)) #通过, ; \ .其中一个进行分割成单词

compile(将匹配的规则重复使用)

1
2
3
4
5
6
import re  #正则表达式RegEx进行文字匹配

#compile()
#使用compile过后的正则,对这个正则重复使用
compiled_re=re.compile(r"r[ua]n") #匹配的是run/ran
print(compiled_re.search("dog ran to cat")) #匹配ran/run --> ran

小抄

小练习-爬百度百科

步骤和要求

1
2
3
4
5
6
1.设定基础url路径
2.设定his存放/item/页面
3.设置url路径
4.读取url路径
5.将html设置到soup内部
6.输出相关的标题或者其他内容

爬取一个页面

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
from urllib.request import urlopen #python自带的打开
import re #正则表达式RegEx进行文字匹配
from bs4 import BeautifulSoup #bs4里面的
import random

#观看规律
#<a target="_blank" href="/item/%E8%9C%98%E8%9B%9B/8135707" data-lemmaid="8135707">蜘蛛</a>
#<a target="_blank" href="/item/%E8%A0%95%E8%99%AB">蠕虫</a>
#<a target="_blank" href="/item/%E9%80%9A%E7%94%A8%E6%90%9C%E7%B4%A2%E5%BC%95%E6%93%8E">通用搜索引擎</a>

#基础url路径
base_url="https://baike.baidu.com"
#将/item/...的页面都放在his中
his=["/item/%E7%BD%91%E7%BB%9C%E7%88%AC%E8%99%AB/5162711"]

#根据基础url+his的地址
url=base_url+his[-1] # 爬取网页为:https://baike.baidu.com/item/%E7%BD%91%E7%BB%9C%E7%88%AC%E8%99%AB/5162711
#将html放在soup里
html=urlopen(url).read().decode('utf-8')
soup=BeautifulSoup(html,features='lxml')
print(soup.find('h1').get_text()) #获取页面的h1标题
print('url:',his[-1])

for循环爬取

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34

from urllib.request import urlopen #python自带的打开
import re #正则表达式RegEx进行文字匹配
from bs4 import BeautifulSoup #bs4里面的
import random

#观看规律
#<a target="_blank" href="/item/%E8%9C%98%E8%9B%9B/8135707" data-lemmaid="8135707">蜘蛛</a>
#<a target="_blank" href="/item/%E8%A0%95%E8%99%AB">蠕虫</a>
#<a target="_blank" href="/item/%E9%80%9A%E7%94%A8%E6%90%9C%E7%B4%A2%E5%BC%95%E6%93%8E">通用搜索引擎</a>

#基础url路径
base_url="https://baike.baidu.com"
#将/item/...的页面都放在his中
his=["/item/%E7%BD%91%E7%BB%9C%E7%88%AC%E8%99%AB/5162711"]

for i in range(5):
#根据基础url+his的地址
url=base_url+his[-1] # 爬取网页为:https://baike.baidu.com/item/%E7%BD%91%E7%BB%9C%E7%88%AC%E8%99%AB/5162711
#将html放在soup里
html=urlopen(url).read().decode('utf-8')
soup=BeautifulSoup(html,features='lxml')
print(soup.find('h1').get_text()) #获取页面的第一个h1标题
print('url:',his[-1]) #获取页面的标签下的地址

#找到所有url
sub_urls=soup.find_all("a",{
"target":"_blank",
"href":re.compile("/item/(%.{2})+$")}) #找到所有a标签 然后target="_blank" href标签都是/item/...
if len(sub_urls) != 0:
his.append(random.sample(sub_urls,1)[0]['href']) #如果可以就往下继续找 找到下一个标签的第一个位置
else:
his.pop() #如果没有就往回走一个页面
print(his)

Requests

get和post区别

1
2
1.get:取得(被动)	
2.post:发送(主动)控制了服务器返回的内容,可以进行个性化服务

request get请求

1
2
3
4
5
6
import requests
import webbrowser
param={"wd":"莫烦Python"} #wd=莫烦Python
r=requests.get('http://www.baidu.com/s',params=param)
print(r.url)
webbrowser.open(r.url) #用py打开默认浏览器

request post请求

1
2
3
4
5
import requests
import webbrowser
data={'firstname':'莫烦','lastname':'周'}
r=requests.post('https://pythonscraping.com/pages/files/processing.php',data=data)
print(r.text)

上传照片

1
2
3
4
5
import requests
import webbrowser
file = {'uploadFile': open('./1.jpg','rb')}
r=requests.post('http://pythonscraping.com/files/processing2.php',files=file)
print(r.text)

登录

1
2
3
4
5
6
7
8
9
10
11
12
13
14
1.使用 post 方法登录了第一个红框的 url
2.post 的时候, 使用了 Form data 中的用户名和密码
3.生成了一些cookies

import requests
import webbrowser
from requests.packages.urllib3.exceptions import InsecureRequestWarning
requests.packages.urllib3.disable_warnings(InsecureRequestWarning)
payload={'username':'Lark','password':'password'} #登录的账号和密码
r=requests.post('http://pythonscraping.com/pages/cookies/welcome.php',data=payload) #将账号密码通过post上传
print(r.cookies.get_dict()) #生成cookies

r=requests.get('http://pythonscraping.com/pages/cookies/profile.php',cookies=r.cookies,verify=False) #通过以前的cookies传入get请求 就可以通过已登录的名义访问get页面
print(r.text)

使用Session登录

1
2
3
4
5
6
7
8
9
10
11
12
import requests
import webbrowser
from requests.packages.urllib3.exceptions import InsecureRequestWarning
requests.packages.urllib3.disable_warnings(InsecureRequestWarning)

session=requests.Session() #获取session
payload={'username':'Lark','password':'password'} #登录的账号和密码
r=requests.post('http://pythonscraping.com/pages/cookies/welcome.php',data=payload) #将账号密码通过post上传
print(r.cookies.get_dict()) #生成cookies

r=requests.get('http://pythonscraping.com/pages/cookies/profile.php',cookies=r.cookies,verify=False) #通过以前的cookies传入get请求 就可以通过已登录的名义访问get页面
print(r.text)

下载文件(urllib.urlretrieve)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
import requests
import webbrowser
from requests.packages.urllib3.exceptions import InsecureRequestWarning
requests.packages.urllib3.disable_warnings(InsecureRequestWarning)
import os
from urllib.request import urlretrieve

os.makedirs('./img/',exist_ok=True) #设定一个img文件夹
IMAGE_URL="https://static.mofanpy.com/static/img/description/learning_step_flowchart.png" #图片地址

urlretrieve(IMAGE_URL,'./img/image1.png') #urllib模块提供一个下载功能urlretrieve

r=requests.get(IMAGE_URL)
with open('./img/image2.png', 'wb') as f:
for chunk in r.iter_content(chunk_size=32): #可以通过控制每个chunk的大小 将大的文件按照一个个chunk存放
f.write(chunk)

小练习-下载美图

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
import requests
import webbrowser
from requests.packages.urllib3.exceptions import InsecureRequestWarning
requests.packages.urllib3.disable_warnings(InsecureRequestWarning)
import os
from urllib.request import urlretrieve
from bs4 import BeautifulSoup

#获取url路径
URL="http://www.nationalgeographic.com.cn/animals/"
#用soup找到带有img_list的这种ul标签
html=requests.get(URL).text
soup=BeautifulSoup(html, 'lxml')
img_ul=soup.find_all('ul', {"class": "img_list"}) #找到所有ul标签里class=img_list
#从ul中找到所有的img,然后提取img的src属性(图片的网址)
for ul in img_ul:
imgs=ul.find_all('img') #获取所有img图片
url = img['src'] #url就是所有img图片的地址
r = requests.get(url, stream=True)
image_name = url.split('/')[-1]
with open('./img/%s' % image_name, 'wb') as f:
for chunk in r.iter_content(chunk_size=128):
f.write(chunk)
print('Saved %s' % image_name)

加速爬虫(多进程分布式)

分布式爬虫(multiprocessing)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
import multiprocessing as mp
import time
from urllib.request import urlopen,urljoin
from bs4 import BeautifulSoup
import re
#基本路径url
base_url='https://mofanpy.com/'

#爬取网页crawl
def crawl(url):
response = urlopen(url)
time.sleep(0.1) # slightly delay for downloading
return response.read().decode()

#解析网页parse
def parse(html):
soup=BeautifulSoup(html,'lxml')
urls=soup.find_all('a',{"href":re.compile('^/.+?/$')})
title=soup.find('h1').get_text().strip()
page_urls = set([urljoin(base_url, url['href']) for url in urls]) # 去重
url = soup.find('meta', {'property': "og:url"})['content']
return title, page_urls, url

加速爬虫(异步加载Asyncio)

Asyncio库

1
2
3
1.Python的原装库
2.Python3.5之后
3.Python3.5:async和await协同工作

普通代码执行

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
import time

#我们的job是按顺序执行的
#必须执行完job1才能开始执行job2
#而且job1需要1秒的执行时间,而job2需要2秒. 所以总时间是3秒多.

def job(t):
print('Start job:',t)
time.sleep(t) # wait for "t" seconds
print('Job',t,'takes:',t,'s')

def main():
[job(t) for t in range(1, 3)]

t1=time.time()
main()
print("NO async total time:",time.time()-t1)

async版代码执行

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
import asyncio
import time

async def job(t):
print('Start job:',t)
await asyncio.sleep(t) # wait for "t" seconds
print('Job',t,'takes:',t,'s')

async def main(loop):
tasks = [
loop.create_task(job(t)) for t in range(1, 3)
] # 创建任务, 但是不执行
await asyncio.wait(tasks) # 执行并等待所有任务完成


t1=time.time()
loop=asyncio.get_event_loop() # 建立 loop
loop.run_until_complete(main(loop)) # 执行 loop
loop.close() # 关闭 loop
print("Async total time:", time.time()-t1)

aiohttp

aiohttp介绍:

1
2
1.aiohttp:可以将requests替换成aiohttp(换成异步requests)
2.aiohttp官网:https://docs.aiohttp.org/en/stable/index.html

一般的requests模块:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
import time
import requests

#url地址
URL='https://mofanpy.com/'

def normal():
for i in range(5):
r=requests.get(URL) #获取url地址
url=r.url
print(url)

t1=time.time()
normal()
print("普通的全部时间:",time.time()-t1)

aiohttp模块:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
import time
import requests
import aiohttp

async def job(session):
response = await session.get(URL) # 等待并切换
return str(response.url)

async def main(loop):
async with aiohttp.ClientSession() as session: # 官网推荐建立 Session 的形式
tasks = [loop.create_task(job(session)) for _ in range(2)]
finished, unfinished = await asyncio.wait(tasks)
all_results = [r.result() for r in finished] # 获取所有结果
print(all_results)

t1 = time.time()
loop=asyncio.get_event_loop() #建立loop
loop.run_until_complete(main(loop)) #执行loop
loop.close() #关闭loop
print("Async total time:", time.time() - t1)

Selenium

概念和安装

1
2
3
4
1.概念:它能够控制你的浏览器,有模有样地学人类"看"网页
2.安装:
2.1 pip3 install selenium
2.2 分为linux和macos/windows区别

Firefox浏览器插件(Katalon Recorder)

1
2
3
1.下载:https://addons.mozilla.org/en-US/firefox/addon/katalon-automation-record/
2.打开插件点击record进行网页操作
3.打开插件点击Export进行浏览代码

Python控制浏览器

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
from selenium import webdriver

#打开火狐FireFox浏览器
#selenium.common.exceptions.WebDriverException: Message: ‘chromedriver' 就需要去根据chrome版本下载exe文件然后放在对应位置
driver=webdriver.Chrome(executable_path=r"D:\python\PyCharm 2021.1.1\plugins\python\helpers\typeshed\scripts\chromedriver.exe")

#将火狐插件Export记录的代码放入
driver.get("https://mofanpy.com/")
driver.find_element_by_xpath(u"//img[@alt='强化学习 (Reinforcement Learning)']").click()
driver.find_element_by_link_text("About").click()
driver.find_element_by_link_text(u"赞助").click()
driver.find_element_by_link_text(u"数据处理 ▾").click()
driver.find_element_by_link_text(u"网页爬虫").click()

#得到网页html
html=driver.page_source
driver.get_screenshot_as_file("./img/screenshot1.png")
driver.close()

Scrapy爬虫库

1
2


双碳大赛-垃圾分类

题目

1
2
1.题目:垃圾分类的处理与数据分析
2.技术:机器学习+深度学习

数据集

1
2
3
4
1.Kaggle:https://www.kaggle.com/account/login?phase=startRegisterTab&returnUrl=%2F
2.UCI:http://archive.ics.uci.edu/ml/index.php
3.百度:https://github.com/GokouRuri7/TacoSSD
4.阿里云:https://github.com/Hmbb0606/ResNet50_Garbage_sorting

torchvision简介

1
2
3
4
5
6
7
8
9
10
import torch
from torchvision import datasets
from torchvision import models
from torchvision import transforms
from torchvision import utils
# torchvision是pytorch的一个图形库 --> 主要用来构建计算机视觉模型
# torchvision.datasets : 用来进行数据加载(有很多图片数据集)
# torchvision.models: 包含常用的模型结构(含有预训练模型) [AlexNet/VGG/ResNet/SqueezeNet/DenseNet]
# torchvision.transforms: 常用的图片变换 [裁剪/旋转] -- 操作对象通常是PIL Image/torch.tensor类型的图像数据
# torchvision.utils: 其他一些有用的方法

models包

1
2
3
4
5
6
7
8
9
#1.使用models中的数据集
##1.快速创建一个权重随机初始化的模型
resnet18=models.resnet18()
alexnet=models.alexnet()
squeezenet=models.squeezenet1_0()
densenet=models.densenet161()
##2.通过pretrained=True来加载一个别人预训练好的模型
resnet18=models.resnet18(pretrained=True) # pretrained设置为True,返回一个使用ImageNet数据集预训练过的模型,会下载权重并存储在缓存路径下
alexnet=models.alexnet(pretrained=True,progress=True) # progress设置为True,显示下载进度条

transforms包

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
#2.使用transforms包(Compose类)
transforms.Compose([
#1.以输入图像的中心为裁切中心,对图像进行裁切
#1.1size取值: 1.int型数字表示裁剪成size大小的正方形 2.(h,w)表示裁剪成h*w大小
transforms.CenterCrop(size=10),
#2.以输入图像的任意点为裁切中心,对图像进行裁切
#2.1size取值: 1.int型数字表示裁剪成size大小的正方形 2.(h,w)表示裁剪成h*w大小
#2.2pad_if_needed取值: 当指定当图像小于裁切后的大小时是否进行pad填充
#2.3padding取值: 1.int型表示每个边缘都进行pad填充 2.Sequence为2表示对左右边界、上下边界进行不同宽度的pad填充/Sequence为4表示对左右边界、上下边界进行不同宽度的pad填充
#2.4fill取值(当padding_mode参数为“constant”时有效): 1.数字类型(torch.Tensor) 2.str类型 3.元组类型(长度为3表示分别对R,G,B三个通道进行填充)
#2.5padding_mode取值: 1.constant使用一个常量进行填充,由fill参数进行指定 2.edge使用图片最外侧边缘的像素颜色填充 3.reflect使用图片的镜像图像对边缘进行填充,最边缘的像素不重复 4.symmetric使用图片的镜像图像对边缘进行填充,最边缘的像素重复一次
transforms.RandomCrop(size=10,pad_if_needed=False),
#3.图像边缘进行Pad填充
#3.1padding取值: 1.int型表示每个边缘都进行pad填充 2.Sequence为2表示对左右边界、上下边界进行不同宽度的pad填充/Sequence为4表示对左右边界、上下边界进行不同宽度的pad填充
#3.2fill取值(当padding_mode参数为“constant”时有效): 1.数字类型(torch.Tensor) 2.str类型 3.元组类型(长度为3表示分别对R,G,B三个通道进行填充)
#3.3padding_mode取值: 1.constant使用一个常量进行填充,由fill参数进行指定 2.edge使用图片最外侧边缘的像素颜色填充 3.reflect使用图片的镜像图像对边缘进行填充,最边缘的像素不重复 4.symmetric使用图片的镜像图像对边缘进行填充,最边缘的像素重复一次
transforms.Pad(padding=10,fill=0,padding_mode='constant')
transforms.ToTensor() #图像转换成torch.Tensor格式
#4.输入只能是torch.Tensor
transforms.Normalize(mean=[0.5,0.5,0.5],std=[0.1,0.1,0.1]) #tensor图像进行标准化转换 mean是均值 std是标准差
transforms.ConvertImageDtype(torch.float), #tensor图像转换成torch.float类型
#5.数据类型转换(tensor/numpy.ndarray --> PIL Image)
#5.1 mode取值: 表示输入数据的色彩空间或像素深度 1.None则实际的mode和输入图像的通道数有关 2.RGBA为输入有四个通道 3.RGB为输入有三个通道 4.LA为输入有两个通道
transforms.ToPILImage(mode=None)
#6.数据类型转换(PIL Image --> tensor)
image=Image.open(r"/path/to/image.jpg")
img_tensor=transform.ToTensor()(image)
])

datasets包

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
#3.datasets包 -- 包中的类几乎都直接/间接继承自torch.utils.data.DataSet类 -- 借由datasets包得到的数据集都可以再传递给torch.utils.data.DataLoader(多线程并行加载样本数据)
data=torchvision.datasets.ImageNet()
data_loader=torch.utils.data.DataLoader(data,batch_size=4,shuffle=True,num_workers=args.nThreads) #并行加载一个ImageNet数据集

#3.1 加载常用数据集
#root: 表示存放mnist数据集的根目录(如果加载的是训练集这个参数就表示训练集的根目录,如果加载的是测试集这个参数就表示测试集的根目录)
#train: True表示训练集,False表示测试集
#transform: 可调用函数类型(输入图片必然是PIL Image格式的)
#target_transform: 可调用函数类型(类对目标进行变换)
#download:
torchvision.datasets.MNIST(root,train=True,transform=None,target_transform=None,download=False)
#3.2 加载用户自定义数据集(ImageFolder类) --一种方式组织(不同类别的数据放在不同目录下,每个目录的名字就是数据的标签)
torchvision.datasets.ImageFolder(root,transform=None,target_transform=None,loader=default_loader,is_valid_file=)
dataset = ImageFolder("train_data/")
print(dataset.classes) #list类型的类名
print(dataset.class_to_idx) #list类型的标签
print(dataset.imgs) #list类型(图片名称和类型组成)
print(dataset[0]) #对应图像的数据

utils包

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
#4.utils包(一些计算机视觉领域经常用到的操作)
##4.1 make_grid函数 --> 将若干张图像拼成一幅图像
###4.1.1 tensor: 1.Tensor类型必须是四维B×C×H×W,用来表示一组mini-batch的Tensor 2.List类型必须是一组大小相同的图片
###4.1.2 nrow: 表示组成的大图中每一行包括的小图的数量
###4.1.3 padding: 表示每张小图四周的padding大小
###4.1.4 normalize: 1.True表示图像会被标准化(控制在(0,1)范围内,最大值最小值通过batch中所有图像的最大值最小值决定)
###4.1.5 value_range: 用元组(min,max)作为标准化图像时用到的最大值和最小值
###4.1.6 scale_each: 1.True表示每个图片使用自己的最值
###4.1.7 pad_value: 表示pad填充的像素的颜色
torchvision.utils.make_grid(tensor, nrow=8, padding=2, normalize=False,value_range=None, scale_each=False, pad_value=0)

##4.2 save_image函数 --> 将给定的Tensor保存成图片
###4.2.1 tensor: 1.如果给定的是一个mini-batch的Tensor,会自动调用make_grid函数将图片组合成网格形式再保存 2.List类型
###4.2.2 fp: 将图片保存到该参数指定的文件路径/文件对象 1.string类型/文件对象(file object)类型
###4.2.3 format: 1.fp为文件名,则忽略 2.fp为文本对象,则参数经常被使用
torchvision.utils.save_image(tensor,fp,format=None)
##4.3 draw_bounding_boxes函数 --> 将给定的图像中画出bounding box。输入的图像必须是uint8类型,且范围在0到255之间
###4.3.1 image:Tensor类型 表示被操作的图片 Tensor大小为C×H×W,dtype类型为uint8
###4.3.2 boxes:Tensor类型 如果一张图像上有N个bounding box (box的四个点以(xmin, ymin, xmax, ymax)的形式进行组织) --注意,这个坐标是图像上的绝对坐标。
torchvision.utils.draw_bounding_boxes(image,boxes,labels=None,colors,fill=False,width=1,font=None,font_size=10)

##4.4 draw_segmentation_masks函数
###4.4.1 image:Tensor类型,大小是(3, H, W),类型是uint8
###4.4.2 masks:Tensor类型,大小是(num_masks, H, W)或(H, W),dtype是bool类型
###4.4.3 alpha:float类型,大小在0到1之间,表示mask的透明度,0表示完全透明,1表示不透明
###4.4.4 colors:list类型或None。list类型来指定每个mask的颜色,颜色可以用字符串"red"或"#FF00FF"来表示,也可以用RGB元组(0, 255, 255)表示
torchvision.utils.draw_segmentation_masks(image, masks, alpha=0.8, colors=None)
,