基本数据类型:
1.整数(int) 8
2.浮点数(float) 6.8
3.字符串(str) "hello" "8"
4.布尔值(bool) true false
Python编码风格指南:
https://python.freelycode.com/contribution/detail/47
序列:指它的成员都是有序排列,并且可以通过下标偏移量访问到它的一个或几个成员。
字符串 “abcd” 、列表 [0,"abcd"] 、元组 ("abc","def") 三种类型都属于序列,列表(list)和元组(tuple)的区别是列表中存储的内容是可变更的,元组中存储的是不可变更的。
序列的基本操作:
成员关系操作符(in 、not in) 判断成员是否在序列当中
连接操作符(+) 序列 + 序列
重复操作符(*) 序列 * 整数
切片操作符([:])
str = "abcdefgdggd" str[2] = "c" str[0:4] = "abc" str[-1] = "d"
字符串通过下标来访问的时候,下标-1代表访问最后一个,0:4代表从第0个到第4个(不包括第4个)
字符编码笔记:ASCII,Unicode 和 UTF-8
http://www.ruanyifeng.com/blog/2007/10/ascii_unicode_and_utf-8.html
条件和循环语句
-
if条件语句
1 if关键字判断条件表达式为真时,执行代码块
if 表达式:
代码块
2 if语句还可以和else、elif(else-if)语句组合成更复杂的判断
if 表达式:
代码块
elif 表达式:
代码块
else 表达式:
代码块
-
while循环语句
while 表达式:
代码块
while循环中通常使用break 和 continue 来终止循环,break是终止整个while循环,continue只是终止满足条件的某次循环,但是会继续向后执行
-
for循环语句
for 迭代变量 in 可迭代对象:
代码块
python中映射的类型:字典(dict)
字典包含哈希值和指向的对象 {“哈希值”:"对象"},例如{'width':10,'heigh':50}
文件内建函数和方法(也就是python默认自带的)
open() 打开文件
read() 输入
readline() 输入一行
seek() 文件内移动
write() 输出
close() 关闭文件
异常
异常不等于错误,异常是在出现错误时采用正常控制流以外的动作。异常处理的一般流程是:
检测到错误,引发异常;对异常进行捕获的操作
try:
<监控异常>
except Exception[resson]:
<>
finally:
<无论异常是否发生都执行>
函数:函数是对程序逻辑进行结构化的一种方法
函数的定义:
def 函数名称():
代码
return 需要返回的内容
函数的调用:
函数名称()
函数的可变参数
函数中定义参数是直接通过 fun(a,b,c)这种形式定义,注意:这种参数是必须的参数,函数调用时必须传3个参数,否则会报错
如果需要定义可变参数,在参数前面需要加。例如 fun(a,*b) ,这样a就是必须参数,后面可以跟一个或多个可变参数,也可以不跟
函数的变量作用域
在函数内部定义一个和函数外面变量同名和变量,分别赋不同的值。在函数里面使用变量,用的是函数内部赋予的值,函数外使用变量则是函数外面赋予的值。
要想使函数内部的赋值外面也能访问到,需要使用global 来修饰
如下:函数func()内部打印的var1和外面通过print(var1)打印的var1的值都是456,因为函数内部var1用global修饰了。如果func()内var1不用global修饰,外面通过print()打印的var1值是123
var1 = 123
def func():
global var1
var1 = 456
print(var1)
func()
print(var1)
函数的迭代器与生成器
我们使用for in 来进行遍历获取每一个数据的时候其实就是使用的迭代器
生成器也是迭代器的一种,通过yield关键字来使用的,可以理解为生成器是带yield的迭代器。通过生成器可以自己构建需要的迭代器
def frange(start, stop, step):
x = start
while x < stop:
yield x
x += step
for i in frange(10,20,0.5):
print(i)
Lambda表达式
当使用一些比较简单的函数,仅仅做一些数值计算时,我们没有必要定义它的函数名和返回值。通过一种更简洁的形式来表示,就是Lambda表达式。形式如下:
lambda 参数 :返回值 例如 lambda a, b : a + b
def add(x,y):
return x+y
lambda x,y: x+y
内建函数
就是python内部提供的一些函数,方便我们使用。例如 filter() map() reduce() zip()
学习内建函数可以在python官网查看文档:https://docs.python.org/3/
-
filter使用:第一个参数传需要满足的函数或者空,第二个参数传数据。filter函数表示从所有数据中过滤出来满足条件的
注意:python 3.x版本与2.x的区别是3.x版本的filter函数必须强制转换为list,否则filter不会执行
a=[1,2,3,4,5,6,7]
print(list(filter(lambda x:x>2 , a)))
- map函数:第一个参数是传入的函数,第二个参数是可变参数,可以传一个或多个。map是对所有的数据经都过第一个传入的函数的规则,生成一个新的数据集合
a=[1,2,3]
map(lambda x:x ,a)
# result: [1,2,3]
print(list(map(lambda x:x+1 ,a)))
# result: [2,3,4]
b=[4,5,6]
list(map(lambda x,y:x+y ,a,b))
# result: [5,7,9]
-
使用reduce之前首先需要使用functools模块导入reduce,第一个参数是函数,第二个参数是序列,第三个参数是初始值。初始值不是必须的
如下:通过reduce函数,将初始值1按照lambda函数与列表中第一个元素2相加,然后将相加的结果 再按照lambda表达式与第二个元素3相加,依次执行。
from functools import reduce
print(reduce(lambda x,y: x+y ,[2,3,4],1 ))
# 10
# >>> ((1+2)+3)+4
-
zip函数:可以对字典的key和value进行对调
zip对两个元组(1,2,3) 和(4,5,6)处理,得到一个zip对象。通过迭代可以得到对调之后的值
for i in zip((1,2,3),(4,5,6)):
print(i)
dicta = {'a':'aa','b':'bb','c':'cc'}
newdict = zip(dicta.values(),dicta.keys())
print(newdict)
print(dict(newdict))
闭包
内部函数引用外部函数的变量,这种形式就叫做闭包。在闭包中,外部函数返回的是内部函数名称。使用闭包,由原来传递变量的方式变为传递函数的方式,使用闭包传递的参数比使用普通函数要少,而且代码可以更加优雅。
def func():
a = 1
b = 2
return a+b
def sum(a):
def add(b):
return a+b
return add
# add 函数名称或函数的引用
# add() 函数的调用
num1 = func()
print(num1)
num2 = sum(2)
print( num2(4))
print(type(num1)) #num1是int类型
print(type(num2)) #num2是function类型
闭包实现计数器:每次调用加1
def counter(FIRST = 0):
num = [FIRST]
def add_one():
num[0] += 1
return num[0]
return add_one
add_one1 = counter(4)
add_one2 = counter(10)
print(add_one1())
print(add_one1())
print(add_one1())
print(add_one1())
print(add_one2())
print(add_one2())
print(add_one2())
闭包使用
# a * x + b = y
def a_line(a,b):
def arg_y(x):
return a*x+b
return arg_y
line1 = a_line(3, 5)
line2 = a_line(5,10)
print (line1(10))
print (line1(20))
print (line2(10))
print (line2(20))
# 使用lambda表达式来定义闭包
def b_line(a, b):
return lambda x: a * x + b
line3 = b_line(2,3)
print(line3(5))
print(line3(2))
装饰器
在一个函数上面通过 @函数名 的方式定义的就是装饰器,@后面的函数是装饰函数,@下面定义的函数是被装饰函数。通过装饰器可以对一些代码进行复用,只要在函数名上加上 @装饰器方法名 就可以了
装饰器的调用是被装饰函数作为参数传递给装饰函数,然后依次执行装饰函数内部的方法。装饰器的定义和闭包非常相似,只是闭包传递的参数和函数内部引用的都是变量,而装饰器传递和内部引用的都是函数
# 不带参数的装饰器
import time
def timmer(func):
def wrapper():
start_time = time.time()
func()
stop_time = time.time()
print("运行时间是 %s 秒 " % (stop_time - start_time))
return wrapper
@timmer
def i_can_sleep():
time.sleep(3)
i_can_sleep()
# 带参数的装饰器
def tips(func):
def nei(a,b):
print('start')
func(a,b)
print('end')
return nei
@tips
def add(a,b):
print(a + b)
add(4,7)
def new_tips(arg):
def tips(func):
def nei(a,b):
print('start %s %s' %(arg,func.__name__))
func(a,b)
print('stop')
return nei
return tips
@new_tips('sub_module')
def sub(a,b):
print(a - b)
@new_tips('mult_module')
def mult(a, b):
print(a * b)
sub(5,1)
mult(2,7)
模块
模块是在代码量变得相当大之后,为了将需要重复使用的有组织的代码段放在一起,这部分代码可以附加到现有的程序中,附加的过程叫做导入(import)
导入模块的一般写法:
import 模块名称
from 模块名称 import 方法名
# 两种导入模块的方式,对于第一种方式当模块名称比较长的时候,可以通过 (import 模块名称 as 简称) 的方式来导入,可以方便地使用 简称.方法名 来调用
# 方式一:import 模块名称
import time
print('a')
time.sleep(1)
print('b')
import time as t
t.sleep(5)
# 方式二:from 模块名称 import 方法名
from time import sleep
print('c')
sleep(2)
print('d')
PEP8编码规范(python编写的代码规范)
PEP8(英文原文):https://www.python.org/dev/peps/pep-0008/
PEP8(中文翻译):https://wiki.woodpecker.org.cn/moin/PythonCodingRule
类与实例
# 面向过程编程
user1 = {'name':'tom','hp':100}
user2 = {'name':'jerry','hp':80}
def print_role(rolename):
print('name is %s,hp is %s' %(rolename['name'],rolename['hp']))
print_role(user1)
# 面向对象编程
# 定义一个类,类名首字母规定要大写,类通过class修饰
class Player():
# sele表示的是类的实例化对象本身,类中定义的每个方法的第一个参数都要self
# 类中定义的变量叫做类的属性,定义的函数叫做类的方法。如下 name和hp就是Player类的属性,print_role()就是Player类的方法
# __init__表示当引用到类时做的事情,如 user1 = Player('ming',220) 就应用到了Player类,将 'ming'赋值给user1.name, 220 赋值给user1.hp
def __init__(self,name,hp):
self.name = name
self.__hp = hp
# 定义一个方法
def print_role(self):
print('%s:%s' %(self.name,self.__hp))
# 定义一个方法更新name
def update_name(self,newname):
self.name = newname
# 类的实例化
user1 = Player('ming',220)
user2 = Player('jie',560)
user1.print_role()
user2.print_role()
user1.update_name('haha')
user1.print_role()
# 类也可以直接通过 实例名.属性 的方式来修改属性值
user1.name = 'san'
user1.print_role()
# 当类中的属性不想让别人访问修改的时候,可以在属性前面加__,这样别人就无法修改了
# 虽然给user1.__hp重新赋值了, 但是因为__hp无法被访问修改,所以__hp值还是之前的值,并没有改变
user1.__hp = 20
user1.print_role()
# 当我们定义一个类,暂时不想对类进行编写功能的时候,可以在类中用''对类进行说明,并且跟上pass,不让类报错
class Monster():
'定义一个怪物类'
pass
如何增加类的属性和方法
增加属性:在__init__(self)
方法中直接将增加的属性在类实例化的时候通过参数传进来,并赋值给self的属性就可以了。
类可以直接通过 实例名.属性 的方式来修改属性值
当类中的属性不想让别人访问修改的时候,可以在属性前面加__,这样别人就无法修改了
增加方法:和定义其他方法一样,在类中定义自己需要的方法就可以
类的继承
在python3中所有的对象都是class类型,像list、字符串str、int等都是。所有的类都继承自object,通过
isinstance('123',object)
结果为true可以得到str也是继承object
# print(type(123))
#
# list = [1,2,4]
# print(type(list))
# tuple = (1,2,4)
# print(type(tuple))
# dict = {'a':'12','b':12}
# print(type(dict))
#
# print(isinstance(list,object))
# print(isinstance(tuple,object))
# print(isinstance(dict,object))
# print(isinstance(12,object))
# print(isinstance('123',object))
class Monster():
'定义怪物类'
def __init__(self,hp=100):
self.hp = hp
def run(self):
print('移动到某个位置')
def whoami(self):
print('我是怪物父类')
class Animals(Monster):
def __init__(self,hp = 10):
# 直接调用父类super()的__init__(hp)方法将hp值赋给self,不用自己再通过self.hp = hp来设置
super().__init__(hp)
class Boss(Monster):
def __init__(self,hp = 80):
super().__init__(hp)
def whoami(self):
print('我是Boss怪物')
m = Monster()
print(m.hp)
m.run()
m.whoami()
a = Animals(30)
print(a.hp)
a.run()
b = Boss(70)
print(b.hp)
b.run()
b.whoami()
类的使用:自定义with语句
通过在类中自定义with的__enter__
和 __exit__
方法,可以自己来定义捕获异常
class TestWith():
# with 包含了 __enter__ 和 __exit__ 方法
def __enter__(self):
print('start run')
def __exit__(self, exc_type, exc_val, exc_tb):
# 当运行没有异常时,exc_tb is None
if exc_tb is None:
print('exit normal')
else:
print('exit with exception')
with TestWith():
print('test')
# 通过raise手动抛出异常
raise NameError('NameError')
多线程编程
多线程实现生产者和消费者问题
from threading import Thread,current_thread
import time
import random
from queue import Queue
# 定义一个大小为5的队列
queue = Queue(5)
class ProducerThread(Thread):
def run(self):
name = current_thread().getName()
nums = range(100)
global queue
while True:
num = random.choices(nums)
# 生产者将生产的数据放到队列中
queue.put(num)
print('生产者 %s 生产了数据 %s' % (name, num))
t = random.randint(1,3)
time.sleep(t)
print('生产者 %s 睡眠了 %s 秒' % (name, t))
class ConsumerThread(Thread):
def run(self):
name = current_thread().getName()
nums = range(100)
global queue
while True:
num = queue.get()
queue.task_done()
print('消费者 %s 消费了数据 %s' % (name, num))
t = random.randint(1,5)
time.sleep(t)
print('消费者 %s 睡眠了 %s 秒' % (name, t))
p1 = ProducerThread(name = 'p1')
p1.start()
p2 = ProducerThread(name = 'p2')
p2.start()
p3 = ProducerThread(name = 'p3')
p3.start()
c1 = ConsumerThread(name = 'c1')
c1.start()
# c2 = ConsumerThread(name = 'c2')
# c2.start()
网友评论