1、列表解析
列表解析将for循环和创建新元素的代码合并成一行,并自动附加新元素。
squares=[value**2 for value in range(1,9)]
print(squares)
2、range(start,stop,step)
其中第三参数为步长,start若不设置,则缺省为0,step若不设置,缺省值为1.
3、在python3中正常输出汉字
在前面加上u
print(u"汉字测试")
4、列表切片
#列表名[start:stop]
#注意!中间是冒号
其中start是其实索引,stop为终止索引。如想取出列表List1[]中的第2-4个元素,则应写为List1[1:4],这样可取出索引为1,2,3的元素
注意终止索引4对应的元素并不能取到,而可取到的最后元素为其
5、元组
列表是可以修改的,常用于存储收集可变化的数据集。有时需要创建一系列不可修改的元素,元组可以满足这种需求。不可变的列表称为元组。
·元组定义
元组看起来像列表,但用圆括号标志,不用方括号标识。虽然元组的元素不可修改,但存储元组的变量可以重新赋值。如果需要存储的值在程序的整个生命周期内都不变,可使用元组。
#可以这样修改元组的值,可自行print一下验证
square=(10,20)
square=(5,10)
#不可以这样修改元组的值,语句不合法
square=(10,20)
square[0]=(5)
6、if语句
在python中,检查是否相等时,默认是区分大小写的。如果想不区分大小写的话,可以利用lower或者upper函数来实现。
与用and,或用or。
检查某个值包含在列表中用in,检查某个值不包含在列表中用not in。
7、字典
在python中,字典是一系列的键-值对,每个键都与一个值相关,你可以使用键来访问与之相关联的值。与键相关的值可以是数字、字符串、列表乃至字典。
在python中,字典用放在花括号中{}的一些列键值对表示。
若想遍历字典中的值,且字典中有很多的值重复时,可以使用set()函数剔除重复项。
alien_0 = {'color': 'green', 'points': 5}
键—值 对是两个相关联的值。指定键时,Python将返回与之相关联的值。键和值之间用冒号分隔,而键—值对之间用逗号分隔。在字典中,你想存储多少个键—值对都可以。
8、关于单引号和双引号
单引号和双引号无本质区别,但是利用好单引号和双引号可以减少转义字符带来的麻烦。如实字符串中包含单引号时,则可用双引号将字符串包括进去,反之亦然。
9、for
language1={
'wang':'c',
'zhou':'java',
'zhang':'python',
}
for name in language1:
print(name+"'s favourite language is" +" "+language1[name].title())
print(name)
在遍历字典过程中,字典中的值存储在变量name中,在遍历结束后,name中存储最后一个值。
10、列表,数组,字典的联系与区别
Python中的列表本质是动态的数组,它与数组的区别在于:1)数组定义好之后就无法扩容了,而列表在定义好之后可以扩容;2)数组只能同时存储一种类型的数据,而列表可以同时存储不同类型的数据。列表为什么没有数组这样的限制呢?
我们知道数组底层的存储结构是顺序存储结构,这样的结构有这样一些优点:逻辑上相邻的节点在物理位置上也是相邻的,可以节省空间,并且可以实现随机存取(也称直接访问)。创建一个数组时,会在内存中开辟一块固定长度的区域用于直接存储元素,扩容要考虑这块区域的后面是否有存储其他对象,所以数组在定义好之后就无法扩容了。而且在查询时,是根据索引和元素存储大小去计算地址偏移量的,如果元素类型不一致,所占内存空间不相同,就不能实现随机存储,所以数组不能同时存储不同类型的数据;而列表就不同了,它存储的是每个元素在内存中的地址(即引用),当列表中空白占位低于1/3时,会在内存中开辟一块更大的空间,并将旧列表中存储的地址复制到新列表中,旧列表则被销毁,这样就实现了扩容。因为列表存储的是元素的引用这个特性,而引用所占的内存空间是相同的,这样便可以同时存放不同类型的数据了。
Python中的字典底层是通过散列表(哈希表)来实现的, “哈希表是根据关键码值(Key value)而直接进行访问的数据结构。也就是说,它通过把关键码值映射到表中一个位置来访问记录,以加快查找的速度。这个映射函数叫做散列函数,存放记录的数组叫做散列表。”
字典本质也是一个数组,但其索引是键经过散列函数处理后得到的散列值,散列函数的目的是使键均匀地分布在散列表中,并且可以在内存中以O(1)的时间复杂度进行寻址,从而实现快速查找和修改。散列表其实是一个稀疏数组(总是有空白元素的数组称为稀疏数组),散列表里的单元通常叫作表元。在字典的散列表当中,每个键值对都占用一个表元,每个表元都有两个部分,一个是对键的引用,另一个是对值的引用。散列表中散列函数的设计困难在于将数据均匀分布在散列表中,从而尽量减少散列碰撞和冲突(散列冲突指的是在查询过程中通过索引定位到有值的表元时,发现该位置的key和查询的key不相等。高级的散列函数能够使冲突数目最小化。散列冲突在这里不过多描述)。
字典数据的添加和查询过程如下:1)添加:把key通过散列函数转换成一个整型数字(即散列值),把这个值最低的几位数字当作数组存储value的下标,最后再存储value到数组中;2)查询:使用散列函数将key转换为数组的下标,并定位到数组对应位置获取value。
字典为什么是无序的?字典的无序是由两方面构成的:1)上面有说过Python中列表会设法保证大概还有1/3的表元是空的,所以快要达到这个阀值时,原有的散列表会被复制到一个更大的空间中去。在这个过程中会重新对字典的键进行散列化(散列表的大小增加了,那散列值所占位数和用作索引的位数都会随之增加,这样做的目的是为了减少发生散列冲突的概率),生成新的散列值,此时由于散列值的不同,则可能导致键的次序不同;2)另一方面就是就是散列冲突,当添加新键时发生散列冲突(即新键通过散列函数处理得到的散列值和字典中其他键的散列值相同,则需要在散列值中另外再取几位,然后用特殊的方法处理一下,把新得到的数字当作索引来寻找空的表元),新键可能会被安排到另一个位置,于是新添加的元素可能就跑到前面去了。
最后再说一点,因为字典的存储使用了散列表,为了减少散列冲突发生概率,散列表必须是稀疏的,所以字典在内存上的开销是很大的。
Python中列表和字典在时间复杂度的比较
list
dict
查询
查找某个元素的索引:O(1)
搜索某个元素:O(n)
获取某个元素: O(1)
根据键搜索:O(1)
添加
尾部添加:O(1)
任意位置添加:O(n)
键添加:O(1)
删除
尾部删除:O(1)
根据键来删除:O(1)
修改
索引赋值:O(1)
键赋值:O(1)
列表使用[],字典使用{}
11、sorted()函数
sorted(list,key,reverse)
list是给定的列表
key是排序调用的函数,也就是排序依据。
reverse决定是升序还是降序,默认reverse值为False,升序。
for name in sorted(language1,reverse=True):
#这只是一个例子
12、append
append()用于在列表末尾添加新的对象
13.int()获取数值输入
age=input('ur age:')
print(age)
#打印出来依旧是数字,但却被默认为字符串类型
age=int(age)
#将age转换为数值类型
print(age)
if age>8:
print('ur old')
else:
print('ur young')
#若不转换数值类型,会报错
14.终止循环
continue是不执行此次循环,跳回到循环体首语句
break是终止循环,并跳出循环。
15.形参与实参
实参(argument):
全称为"实际参数"是在调用时传递给函数的参数. 实参可以是常量、变量、表达式、函数等, 无论实参是何种类型的量,在进行函数调用时,它们都必须具有确定的值, 以便把这些值传送给形参。 因此应预先用赋值,输入等办法使实参获得确定值。
形参(parameter):
全称为"形式参数" 由于它不是实际存在变量,所以又称虚拟变量。是在定义函数名和函数体的时候使用的参数,目的是用来接收调用该函数时传入的参数.在调用函数时,实参将赋值给形参。因而,必须注意实参的个数,类型应与形参一一对应,并且实参必须要有确定的值。
形参变量只有在被调用时才分配内存单元,在调用结束时,即刻释放所分配的内存单元。因此,形参只在函数内部有效。函数调用结束返回主调用函数后则不能再使用该形参变量。
16. 函数、模块。导入
导入整个模块
import 模块名
导入模块中的特定函数
from 模块名 import 要调用的函数名
模块名.函数名(实参)
下面是一个例子
from pizza import make_pizza
make_pizza(16, 'pepperoni')
make_pizza(12, 'mushrooms', 'green peppers', 'extra cheese')
指定函数别名
from moudle_name import function_name as fn
#fn是别名
导入模块中所有函数
from moudle_name import *
#*运算符可以导入模块中所有参数
所有的import语句都应该放在文件开头,除非文件开头有描述性语句对整个程序进行描述
17、类
Python中,根据约定,首字母大写的名称指的是类。若类定义的括号中是空白的,则需要从空白创建这个类。
类中的函数称为方法。
**···**类中一个容易出错的地方,
__init__函数,这里是两个连续的下划线,少写下划线会报错。
若创建的类中所写方法存在错误,在该方法未被调用时可能不会报错,在调用的时候会报错,需谨慎。
17.1给属性指定初始值
class Car():
def __init__(self,name,type):
#初始化描述汽车的属性
self.name=name
self.type=type
self.age=0
类中的每个属性都必须有初试值,哪怕这个值是0或者空字符串。在有些情况下,如果设置默认值时,在方法__init()__内指定这种初初始值是可行的,若对初始值这样操作,则无需包含为它提供初始值的形参,就比如上述代码中的age
17.2继承
当父类与子类中有同名方法时,会根据实例所属类别调用对应类别的方法。
18、编码风格的规范问题
类命名应该采用驼峰命名法,即将类名中的每个单词的首字母都大写,而不是用下划线。实例名和模块名都采用小写,并在单词之间加上下划线。
·对于每个类,都应该在定义类之后紧跟一个文档字符串,其实就相当于注释,来对此类的进行描述。模块中也需要有文档字符串来描述模块。
·可以使用空行来组织代码,但是不要滥用,在类中,可使用一个空行来分割方法,在模块中则使用两个空行来分割类。
·需要同时导入标准库中的模块和自己创建的模块时,先编写导入标准库中模块的import语句,然后编写导入自己创建的模块的语句,这样让人更易于明白程序使用的各个模块来自何处。
19、处理异常
try-except-else
try代码块中只包含可能出现错误的代码;except代码块中则是指出出现何种错误,采取何种措施的代码;else代码块中包含try代码块中的代码成功运行后需要运行的代码语句。
try:
word a
except Error1:
word b
#若word a在执行时,报错Error1,则执行word b语句
else:
word c
#若word a语句执行成功,则执行word c语句
20、测试
单元测试:用于核实函数的某个方面有没有问题
测试用例:测试用例是一组单元测试,这些单元测试一起核实函数在各种情形下的行为都符合要求。
对于大型项目,在初始阶段一般针对重要行为进行编写测试即可,在项目广泛应用时再进行全覆盖测试。
21、关于导入
两个文件a.py和b.py,在a.py中写主程序,想要导入b中的某一类(例如Book类),两种方法
a.py
#1
from b import Book
book1=Book()
#2
import b
book1=b.Book()
b.py
class Book():
def __init__(self):
class Car():
def __init__(self):
#1和#2两种方式要搭配使用。若采用#1导入某一模块中的类或者方法,那么在创建导入类对象或者调用方法时,直接写类名或者方法名即可;而若采用#2导入整个模块,那么在创建导入类对象或者调用方法时,需要如下格式
模块名.类名(方法名)
否则会报错。
22.
python是以变量的内容为依据分配内存的,例如a=5,b=5.
如果对b进行强制类型转换,那么a的数据类型也会发生相同的变化。
23编码格式
在 Python3 中,文件默认的编码方式是 UTF-8 ,文本字符的常用的编码有 ASCII 和 Unicode 。
看一个示例代码:
str1 = '好好学习,天天向上'
print(type(str1))
a = str1.encode('utf-8')
print(type(a))
print(a.decode('utf-8'))
打印结果如下:
<class 'str'>
<class 'bytes'>
好好学习,天天向上
可以看到,字符串 encode() 编码以后,类型变成了 byte 。