python 原理
语言类型:
分类:编译型、解释型,强类型、弱类型
编译型:编译完在执行
- 代表语言:C,C++
- 优点:运行速度快
- 缺点:开发速度慢
解释型:逐行编译
优点:开发速度快
缺点:运行速度慢
代表语言:Python,JavaS,PHP
编码:
- 8bit = 1byte 1024B(byte) = 1KB 1024KB = 1M
- ASCII: 英文编码 英文一个字节
- GBK : 国标码 英文 一个字节,中文两个两个
- Unicode: 万国码 英文两个 个字节, 中文四个字节
- UTF-8 : 万国码升级 英文一个字节, 欧洲两个字节,中文三个字节
python2和python3区别:
代码: python2 代码混乱,重复 python 源码规范,清晰,简单优美
编码: python2 编码为ascii python3 内存编码为Unicode
print: python2 中print不需要添加括号 python3 中需要添加括号了
input: python2 中输入是raw-input python3 中是input
nonload: python2 中没有nonload python3 中新加入的
类: python2 经典类,深入优先 python3 不存在经典类,都是新式类,mro算法也叫c3
基础数据类型:
字符串:str
- upper,lower,startwith,endswith,replace,strip,split,join,count,isdigit,index/find(不报错)
列表:list
append,insert,extend,pop,remove,del,改:li[] = "海洋" 查:根据索引,切片查询
count,index,sort,reverse
列表的注意事项:
- 循环一个列表时,删除元素时,剩下的值会向前近一步 (索引也会更改),
- 不要改变列表的大小,这样会影响你最终结果
列表去重:
- 方法一:
创建新的列表,for循环列表中每个元素是否不在新列表中,不在则追加
方法二:
l1 = [33,22,33,44,44,22,55,11]
l2 = list(set(l1)) #set去重转成列表
l2.sort(key = l1.index) #使用列表进行排序,保证原顺序
print(l2)
列表删除:
列表删除只可从后往前删除,
a = [1,2,3,4,5,6,7,8] for i in range(len(a)-1,-1,-1):
if a[i] > 5:
a.pop(i)
else:
pass
print(a)
字典:dict
增加:dic['name'] = ['hai'] 有则改之,无则增加 ,dic.setdefault("name","hai") 有则不变,无则增加
删除:dic.pop('key',)
修改:dic['name'] = 'junli'
查看:print(dic['name'],dic.get('name') #get没有返回none,好用!!!
fromkeys:
- 创建空字典:dic = dict.fromkeys("可迭代对象")
enumerate:
- 枚举,for i in enumerate(字典): 每次循环索引位置和key
update:
- dic.update('name','18') 添加
- dic.update(name = '太白金星') 更改
- dic.update([(1, 'a'),(2, 'b')]) 列表中的元祖添加到字典
- dic1.update(dic2) 更新:字典融合,有则覆盖,无则增加
元祖:tuple
只读列表,不可修改
tu1= (1) 如果元祖中只有一个元素,那么他还是本身元素
count 统计元祖中字符出现的次数
index 通过元素查找索引
集合:set
- set集合里存放的是可迭代类型
- 列表去重
- 交集,并集,差集(两个数据进行的操作)
文件操作:
文件操作的格式:
with open('文件的读',encoding='utf-8') as f1:
- print(f1.read())
- with: 使用with打开文件,不用关闭文件句柄
open: 是内置内置函数,调用操作系统的接口
encoding:设置文件读写编码格式,默认是操作系统编码
mode操作方法:
读取:r(默认是r) 追加:a ,写入:w 非文本文件不能指定编码:rb
先读后写(可以追加):r+
追加读:a+
文件句柄操作方法:
- read readline() write() read(n)按光标读 readlines()将内容聚合列表
替换文件:
# 另一种打开文件的方式: 帮助自动关闭文件;可以同时开多个文件,用逗号隔开;也可以同时操作一个文件
with open("a", mode="r", encoding="utf-8") as f,\
open("b", mode="a", encoding="utf-8") as f1: import os
print(os.getcwd()) # 查看当前工作路径
os.remove() # 删除文件
os.rename() # 更改文件名.(新名,旧名)
Python 中的空间和作用域:
三个空间:
内置名称空间:当你运行python程序,会开启一个内置名称空间,将内置函数print等等加载到空间中
全局名称空间:加载当前py文件中的变量,和函数外声明的变量,加载到全局空间中,变量与值对应关系
局部名称空间:函数执行时,会开辟出局部空间(也叫临时名称空间)
globals() 查看全局存储的全局变量
locals() 查看当前存储的变量
全局作用域---->内置名称空间和全局名称空间
局部作用域---->局部名称空间
作用:
作用域对与变量而言,声明变量在程序里可使用的范围
局部作用域可以引用全局作用域变量,局部作用域不能改变全局变量
- 加载顺序:
- 内置--->全局--->局部 (从外到内)
- 取值顺序:
- 就近原则LEGB
同一代码块:
- 优点:能够进行复用,提高一些字符串,这样在数字处理时间和空间上提升性能,节省内存
- 适用对象:
- 列表,字典,可变的数据类型不会复用的
- int:任何数字在同一代码块下都会复用
- str:几乎所有的字符串都会符合缓存机制
不同代码块:
- 小数据池规则:
- 小数据池,是不同代码块下的缓存机制,也叫缓存机制和驻留机制,在编程语言当中都有类似的东西
- 主要是用于提高效率数字类型在时间和空间上的性能,避免创建重复的数据,节省内存
- 缓存规则:
- int:-5-256整数进行缓存,当你将整数赋值给变量时,直接引用已经创建好的缓存对象
- str:
- 1.字符串在做乘法(乘法不为1)的时候长度不能超过20
- 2.自己定义的字符串长度不限制,字符串必须是字母,数字,下划线组成
- 3.特殊字符定义1个的时候,进行驻留
运算符:
- 算数运算符:
* /
加减乘除 %取余 2**4 幂 //整除返回的部分
- 比较运算符:
- == 等于 !+ 不等于 >= 大于等于 <= 小于等于
- 逻辑运算符:
- 顺序:not >>> and >>> or
- x and y x 为真返回y x为假返回x
- x or y x为真返回x x 为假返回y
- not x x为真返回假 x为false返回true
深浅copy:
浅copy:
- 拷贝的数据半共享,当你浅copy一个嵌套的列表,将拷贝第一层数据会指向同一个内存地址,如果你修改数据,指向会断开,第二层数据也就是嵌套的列表他没有拷贝,元素的内存地址是共用的一个。
深拷贝:
拷贝的数据不共享,深拷贝他会逐层判断,将不可变的数据类型指向同一个内存地址,可变的数据类型跟原列表不共用一个,元素指向的内存地址都是一样的。
函数原理:
函数闭包:
闭包存在函数嵌套中,内层函数对外层函数中非全局变量进行了引用或者修改,这个变量就是自由变量,他不会随着函数的运行结束而消失,保证了数据安全
- 当自由变量被调用时,闭包形成
- 判断函数是不是闭包,print(ret.
__code__.co_
freevars)
作用:
- 保证了数据安全性,自由变量不会在内存中消失,而且全局还引用不到
应用环境:
用在与装饰器
开放封闭原则:
- 开放原则:在源码不改变的情况下,增加一些额外的功能
- 封闭原则:不改变源码,对与更改是封闭的。
- 装饰器符合开放封闭原则
函数:
函数是以功能为导向,一个函数封装一个功能,你写完这个函数可以随掉随用,函数他减少了代码的重复性,增强了代码的可读性
高阶函数:
- 一个函数可以作为参数传递给另一个函数,或者一个函数的返回值为另一个函数,递归也是高阶函数
- map filter reduce 都是高阶函数
匿名函数 lambda:一句话函数,用于内置函数,匿名函数结合内置函数使用
- func = lambda x,y : x+y 名字func :前形参 :后返回值
- 示例1:
- func = lambda x : (x[0],x[2]) 返回多个元素加()
- 示例2:
- func = lambda x,y :x if x > y else y
- func = lambda *args : max(args) #返回最大的值,也可以添加三元运算>
- 示例3:
- [lambda :i for i in range(10)] 这样的都是十个为9的内存地址,遇()执行
内置函数:***加key的 dict,abs,sum,min,max,sorted,map,reduce,filter(68种)
float int list dict set tuple id len next type input print help
加key的格式:
- 将最小的值返回,dic[x] 返回值是什么,就按什么比大小***
- dic = {'a':3,'b':2,'c':1}
- print(dic[min(dic,key=lambda x:dic[x])]) key=lambda 函数名 :前形参 :后返回值
函数名应用:
- 函数名就是变量
- 函数名加()执行
- 函数名可以作为容器类型(list)的元素
- 函数名可以作为函数的参数传递
- 函数名可以作为函数的返回值
函数参数:
*的魔法作用:
*args 位置参数聚合成一个元
kwargs 关键位参数聚合成一个元
实参加* 代表打散,聚合给*arg
实参加** 代表打散,只能用于字典,聚合给**kwargs 打散的key不能是int类型
参数说明:
位置参数:从左至右,一一对应
默认参数:传值覆盖,不传则默认
仅限关键字参数:放在默认参数后面
形参顺序:
- 位置参数,*args,默认参数,仅限关键字参数,**kwargs
实参顺序:
- 位置参数,关键字参数,混合参数(位置参数,关键字参数)
注意事项:
- 默认参数的坑,当你的默认参数是可变类型,不会消失,使用的是同一个内存地址。
- 函数名指向的是函数的内存地址,加上()就可执行。
示例:
def func(a,*args,sex='男',c,**kwargs,):
print(a)
print(sex)
print(args)
print(c)
print(kwargs)
func(1,2,3,sex='女',name='海洋',age=18,c='666')
当函数的实参位置不传值的话,可变数据类型不会消失,会使用同一个内存地址
def f(x,l=[]):
for i in range(x):
l.append(i*i)
print(l) f(2)
f(3,[3,2,1])
f(3)
递归函数:
递归函数就是自己调用自己
函数或者其他代码都可以解决递归解决的问题,但是递归在某些时候能够出奇制胜
人理解函数,神理解递归
默认的递归次数:
- 1000(次数越多,速度越慢)
- 递归根本:逆推,要有终止条件return
递归示例1:
#打印列表中的每个值
l2 = [1, 3, 5, ['海洋','俊丽', 34, [33, 55, [11,33]]], [77, 88],66]
def func(alist):
for i in alist:
if type(i) == list:
func(i) # func(['海洋,'俊丽',34]) #当i为列表时一直调用本身,节省for循环
else:
print(i)
func(l2)
递归示例2:
#循环获取路径下的文件
import os
li = []
def dir(path):
path_file = os.listdir(path) #os.listdir 已列表的形式获取目录中文件夹和文件 for i in path_file:
if os.path.isdir(os.path.join(path, i)): #判断是否为目录
dir(os.path.join(path, i)) #将使用jion拼接使用函数再次调用给函数本身
else:
li.append(os.path.join(path, i)) #是文件就返回
return li print(dir(r'路径'))
递归示例3:
import os
import re
li = []
def dir(path):
path_file = os.listdir(path) #os.listdir 已列表的形式获取目录中文件夹和文件 for i in path_file:
if os.path.isdir(os.path.join(path, i)): #判断是否为目录
dir(os.path.join(path, i)) #将使用jion拼接使用函数再次调用给函数本身
else:
li.append(os.path.join(path, i)) #是文件就返回
return li dir(r'E:\Pycharm-代码\作业\23期\day27-网络编程') for png in li:
if re.findall("png",png) == ["png"]: #使用re模块findall判断文件是否已png结尾
jpg = str(png).replace(".png",".jpg") #将png路径替换成jpg
os.rename(png,jpg) #文件重命名
列表推导式:
简单,快捷,装逼
- 循环模式:
- li = [i for i in range(2,101,2)] 构建1-100的偶数
- 筛选模式:
- [i for i in range(1,31) if i %3 ==0 ] if筛选能被3整除的
生成器表达式:
- (i for i in range(1,11)) 使用()扩起来就可以了, 就是生成器表达式
可迭代对象:
可以重复迭代取值的一个工具,内部含有
__iter__
方法的就是可迭代对象查看是否含有可迭代对象方法if
__iter__
in dir()优点:
- 可迭代对象是一个操作方法灵活,侧重于对少量数据灵活处理(并且内存足够)
缺点:
- 占用内存
- 不能迭代取值(索引,字典的key)
迭代器 ltertor:
可以重复迭代的工具,内部含有
__iter__
和__next__
方法就是迭代器,
iter方法是将可迭代对象转换成迭代器
next方法是迭代器进行取值(无法找到下一个结果时会出现StopIteration异常)
优点:迭代取值,节省内存(迭代之后元素消失),惰性机制不走回头路
缺点:操作方法少,不直观,查询速度较慢(时间换空间)
作用:
*为什么要使用迭代器,当你要获取文件内容时,传统方式是读取文件内容到内存空间中,在使用
for循环遍历,如你文件较大,这样会占用极大的内存空间,而使用迭代器是可以一个迭代读取一
段内容,节省内存空间,这也是迭代器存在的作用
- 使用环境:
- 逐行遍历文件内容,构建和扩展集合类型,元祖拆包
生成器:
生成器的本质就是迭代器,函数中包含yield方法,是生成器函数。
生成器产生方式: 生成器函数(yield和yield from) 生成器表达式() python内置函数 lamdba
取值方式:next() for循环 list列表
yield:
- 函数中包含yield方法,是生成器函数,当你去调用函数的时候,返回值是一个生成器地址,当你想执行内容需要调用next()方法
yield from:
代替了生成器函数里的内层循环,在函数中如果yield from list 会将list可迭代对象变成迭代器返回
迭代器和生成器区别:
可迭代对象和迭代器的区别:
可迭代对象操作方法多,但是占用内存,不能循环迭代取值,如果你侧重于数据灵活操作并且内存足够,可以使用可迭代对象
迭代器操作方法少,不灵活,但是可以迭代取值,取完值消失,查询速度慢
迭代器和生成器的区别:
迭代器都是内置函数转化过来的
生成器是我们自己用Python代码构建的
装饰器原理:
- 装饰器本质是一个函数:他要装饰一个函数,在不改变原函数的源码以及调用方式的前提下,给其增加额外的功能
- 语法糖:@index = index = test_time(index)
- 用途:
- 登录认证,打印日志,访问记录
最简单的装饰器函数传参:
def warpper(s): #s = func1
def inner(*args,**kwargs): #4-聚合接受inner的实参海洋
print(666) #执行func1函数前操作
ret = s(*args,**kwargs) #5给打散实参执行func1函数,
return ret #6将func1,return执行结果传给inner
return inner #2-返回inner给warpper @warpper #1-语法糖:func1 = warpper(func1)
def func1(a):
return f"{a}欢迎登录"
print(func1("海洋")) #3-func1 = inner('海洋') 7 print结果
装饰器传参:装饰器嵌套三层函数,最外层函数接受装饰器实参,可以对形参进行操作判断
def wrapper(n):
def wrapper1(f):
def inner(*args,**kwargs):
name = input("输入用户名")
pwd = input("输入密码")
with open(n,encoding='utf-8') as f1: #n等于语法糖传过来的值
for i in f1:
j,k = i.strip().split('|')
if name == j and pwd == k:
ret = f(*args,**kwargs)
return ret
return inner
return wrapper1 @wrapper('qq') #将qq传给最外层wrapper形参
def qq():
print('成功访问qq') @wrapper('weixin')
def tiktok():
print('成功访问微信')
qq()
tiktok()
两个装饰器,装饰一个函数:先执行@wraper1 执行完的结果是@wraper2的形参。
如果两个装饰器内层函数一样,调用函数时先走最上面装饰器
def wrapper1(func1): # func1 = f原函数
def inner1():
print('wrapper1 ,before func') # 2
func1()
print('wrapper1 ,after func') # 4
return inner1 def wrapper2(func2): # func2 == inner1
def inner2():
print('wrapper2 ,before func') # 1
func2() # inner1
print('wrapper2 ,after func') # 5
return inner2 @wrapper2 # f = wrapper2(f) 里面的f == inner1 外面的f == inner2
@wrapper1 # f = wrapper1(f) 里面的f == func1 外面的 f == inner1
def f():
print('in f') # 3
f() # inner2()
模块原理:
模块:
一个.py文件就是模块,节省代码,容易维护,组织结构更清晰
常用的模块:
- json,pickle:序列化,sys:路径,os :文件操作
- hashlib :加密 time datetime:时间
- random:随机取值
- 模块的两种引用方式:
- import 模块名
- from 模块名 import 变量
模块的运行方式:
- 脚本方式:直接用解释器执行,或者pycharm中右键运行。
模块方式:被其他的模块导入,为导入他的模块提供资源(变量,函数定义,)
模块的分类:
- 内置模块:标准库,python解释器自带的,time,os,sys,等等200多种
第三方库(模块):各种大神写的模块,通过pip install...安装的6000多种自己写的模块,
自定义模块
引用模块发生三件事:
- 1,import tbjx 将haiyang.py文件(变量,函数名)加载到内存
- 2,在内存中创建一个以太tbjx命名的名称空间
- 3,通过haiyang.xx名称空间的名字.等方式引用此模块的名字(变量,函数名)
序列化:
- 将一个数据结构(list,tuple,dict)转化成一个特殊序列的过程,并且可以翻转回去,这个转化的过程就是序列化
Json:
- dict,list, tuple,str,int
- 不同语言都遵循使用的一种数据转换格式,可以互相使用json传输数据
Pickle:
支持所有数据类型
python语言遵循的一种数据化转换格式,只能在python中使用
作用:
- 为什么要用序列化,因为硬盘存储和网络传输时只能接受bytes类型的。
- dumps 将数据转换 dump将数据转换并写入文件(json存储空间小,pickle存储空间大)
开发规范:
规范开发:文件加载问题,代码可读性差,查询麻烦
PEP8规范:
1. bin start.py 程序开关:启动代码目录,run()
2. conf settings.py 配置文件:放置一些静态参数,比如文件路径,数据库配置,软件默认设置
3. core src.py 主逻辑函数: 主要存放就是核心逻辑功能,核心函数都在这里
4. lib common.py 公共组件: 存放装饰器,密码加密功能,日志功能存放
5. db register 存放数据库文件, 注册表,用户信息
6. log access.log 存放系统的日志
bin start:启动start文件,工作目录已经写入到sys.path中(内存中),在这个工作目录下的文件都可以互相引用
import os
import sys
#动态获取工作目录os.path.dirname 通过file文件找到父级目录上的父级目录也就是整个代码的工作目录
BASH_PATH = os.path.dirname(os.path.dirname(__file__))
sys.path.append(BASH_PATH) from core import src
if __name__ == '__main__': #防止别的文件引用执行
src.run()
settings:数据库地址进行拼写
import os
BASE_PATH = os.path.dirname(os.path.dirname(__file__))
register_path = os.path.join(BASE_PATH,'db','register')
src:主逻辑需要引用数据库地址和装饰器文件,都需要引用
from conf import settings
from lib import common
common:装饰器这块引用src中的状态和登录函数,规范其实也就是文件之间的互相引用
from core import src
python 原理的更多相关文章
- Python原理 -- 深浅拷贝
python原理 -- 深浅拷贝 从数据类型说开去 str, num : 一次性创建, 不能被修改, 修改即是再创建. list,tuple,dict,set : 链表,当前元素记录, 下一个元素的位 ...
- Python原理 -- 内存管理
语言的内存管理是语言设计的一个重要方面. 它是决定语言性能的重要因素. 无论是 c语言 的手工管理, 还是 Java 的垃圾回收, 都成为语言最重要的特种. 以下以 python 为例, 说明一门动态 ...
- 【python原理解析】python中分片的实现原理及使用技巧
首先:说明什么是序列? 序列中的每一个元素都会被分配一个序号,即元素的位置,也称为索引:在python中的序列包含:字符串.列表和元组 然后是:什么是分片? 分片就是通过操作索引访问及获得序列的一个或 ...
- 【python原理解析】gc原理初步解析
python的gc是会用到:引用计数.标记-清除和分代收集,首先说明一下什么是引用计数 可以通过sys模块中的getrefcount()方法获取某个对象的引用计数 python本身的数据类型有基础类型 ...
- python爬虫(一)_爬虫原理和数据抓取
本篇将开始介绍Python原理,更多内容请参考:Python学习指南 为什么要做爬虫 著名的革命家.思想家.政治家.战略家.社会改革的主要领导人物马云曾经在2015年提到由IT转到DT,何谓DT,DT ...
- python实现PCA算法原理
PCA主成分分析法的数据主成分分析过程及python原理实现 1.对于主成分分析法,在求得第一主成分之后,如果需要求取下一个主成分,则需要将原来数据把第一主成分去掉以后再求取新的数据X’的第一主成分, ...
- Selenium Web自动化 原理
文章转自 白月黑羽教Python 原理 说到web应用自动化测试,第一选择就是 Selenium 框架. Selenium 是一个 Web 应用的自动化框架. 通过它,我们可以写出自动化程序像人一样( ...
- 【Python】python中的装饰器——@
对装饰器本来就一知半解的,今天终于弄清楚了,Python中的装饰器是对装饰者模式的很好运用,简化到骨子里了. python中为什么需要装饰器,看这里:http://www.cnblogs.com/hu ...
- Python高效开发实战——Django、Tornado、Flask、Twisted
今天要推荐的就是这本书,内容涉及四种主流的Python Web开发框架,零基础完成网站搭建.数据库设计.前后端开发,全方位领悟Python原理与应用. 最新最全的框架实战,尽在这本书,可搜索亚马逊.京 ...
随机推荐
- mongose TypeError: Cannot read property 'findOne' of undefined
最近在node的一个项目中,需要在model的一个数据表中写一个钩子函数去调用另外一个文件中的方法,一开始我采用了将此方法放入到global中,直接从global.meteod这样去获取.后来我又尝试 ...
- atitit.提高开发效率---mda 革命性的软件开发方法
atitit.提高开发效率---mda 革命性的软件开发方法 1. 软件开发方式的革命开发工具的抽象层次将再次提升 1 2. 应用框架和事实上现相分离 2 3. 眼下的问题模型和代码不同步 2 4. ...
- hdu4360 spfa+分割点
标题要求必须按照L O V E 行走为了,你必须至少有一个完整的LOVE.说明可以通过同一个点反复 对每一个点拆分为4个点.分别为从L,O,V,E到达. 起始点看做是从E到达的 spfa时发现当前点距 ...
- DDD实战12 值对象不创建表,而是直接作为实体中的字段
这里的值对象如下风格: namespace Order.Domain.PocoModels { //订单地址 //虽然是值对象 但是不继承ValueObject //因为继承ValueObject会有 ...
- uva 11892 - ENimEN(推理)
题目链接:uva 11892 - ENimEN 题目大意:给定n堆石子的个数,两人轮流选择石子堆取石子,直到不能取为失败,附加条件,假设前一次操作,即队手的操作,没有将选中石子堆中的石子取完,那么当前 ...
- cocos2d-x 源代码分析 总文件夹
这篇博客用来整理与cocos2d-x相关的工作,仅仅要有新的分析.扩展或者改动,都会更改此文章. 祝大家愉快~ 1.源代码分析 1.CCScrollView源代码分析 http://blog.csdn ...
- .NET内置的Ajax工作原理
在期望不执行回发(postback)而从客户端运行服务器代码的情况下,可以使用ClientScriptManager类来调用客户端回调(callback).这称为对服务器执行带外回调.在客户端回调中, ...
- 【HLSL学习笔记】WPF Shader Effect Library算法解读之[BandedSwirl]
原文:[HLSL学习笔记]WPF Shader Effect Library算法解读之[BandedSwirl] 因工作原因,需要在Silverlight中使用Pixel Shader技术,这对于我来 ...
- 使用WinPcap获取网卡MAC地址
关键字:WinPcap 网卡 MAC地址 作者:txw1958 在WpdPack_4_1_2\WpdPack\Examples-remote\PacketDriver\GetMacAddress\目录 ...
- Ubuntu+NDK编译openssl(为了Android上使用libcurl且支持HTTPS协议)
为了Android上使用libcurl且支持HTTPS协议,需要依赖openssl,因此先来了解一下如何编译OpenSSL1.编译ARM下的共享库(默认的)我使用的是guardianproject的o ...