Python learning:More Types
None
None 对象可以被用来表示值的缺失。它类似于其他编程语言中的null 。像一些空值,如0,[]以及空字符串,当将这些值转变成布尔变量(Boolean variable)的时候为False 。
当我们在Python操作面输入的时候,None 会表现为空的字符串。
>>>None==None
True
>>>None
>>>print(None)
None
>>>
None 对象可以通过任何没有明确的返回任何值的函数返回得到
示例一:
def some_fun():
print("Hi!")
var=some_fun()
print(var)
Result:
>>>
Hi!
None
>>>
示例二:
foo=print()
if foo==None:
print(1)
else:
print(2)
Result:
1
Dictionaries(字典)
Dictionaries (字典)是用来将任意键映射到值的数据结构。列表可以被认为是带有一定范围内的整数键的dictionaries 。Dictionaries 可以像列表一样使用同样的方式进行检索,使用方括号(square brackets) 将键包含在里面:
示例一:
ages={"Dave":24,"Mary":42,"John":58}
print(ages["Dave"])
print(ages["Marry"])
Result:
>>>
24
42
>>>
如果试图检索不属于dictionary 的键,将会返回KeyError
示例一:
primary={
"red":[255,0,0],
"green":[0,255,0],
"blue":[0,0,255],
}
print(primary["red"])
print(primary["yellow"])
Result:
>>>
[255,0,]
KeyError:'yellow'
>>>
==注意==正如你所看到的,一个dictionary可以存储任何类型的数据作为值,如果是一个空的dictionary可以定义为{}。
示例二:
test={}
print(test[0])
Result:
KeyError:0 #因为test是空的dictionary,没有0这个键
只有不变的 对象才能用做字典的键。不能改变的对象指的是这些不能够被改变的对象。到目前为止,你遇到的唯一可变的 对象就是lists 和dictionaries 。如果试图将一个可变的对象作为字典的键,将会产生TypeError。
bad_dict={
[1,3,4]:"one two four",
}
Result:
TypeError:unhashable type:'list'
和列表一样,dictionary的键可以被指定给任何的值。然而,和列表不同的是,一个新的dictionary键可以被赋予一个新的值,这个值不是之前存在的。
示例一:
squares={1:1,2:4,3:"error",4:16}
squares[8]=64 #给不存在的键赋值
squares[3]=9 #给存在的键重新赋值
print(squares)
Result:
{1:1,2:4,3:9,4:16,8:64}
示例二:
primes={1:2,2:3,4:7,7:17}
print(primes[primes[4]])
Result:
17
为了判断键是否在dictionary中,你可以使用in 或者not in ,就像你在列表中进行的那样。
示例一:
nums={
1:"one",
2:"two",
3:"three",
}
print(i in nums)
print("three" in nums)# in 和not in都是用来判断键的,不能判断值
print(4 not in nums)
Result:
True
False
True
一个有用的dictionary方法就是get ,它可以完成索引能做的事情,但是如果发现键不在dictionary中,它就会返回另外一个指定的值(‘None',默认情况下)
示例一:
pairs={1:"apple",
"orange":[2,3,4],
True:False,
None:"True",
}
print(pairs.get("orange"))
print(pairs.get(7))
print(pairs.get(12345,"not in dictionary"))#键不在pairs中,但是指定了值,所以会返回指定的值
Result:
[2,3,4]
None
not in dictionary
示例二:
fib={1:1,2:1,3:2,4:3}
print(fib.get(4,0)+fib.get(7,5))
Result:
8
#因为fib.get(4,0)中键4是fib中的,所以返回值3,而fib.get(7,5)中键7不是fib中的,所以返回指定的值。
Tuples (元组)
元组与列表也是非常类似的,我们希望元组是不可改变的。同样可以使用括号创建它们,而不是方括号。
words=("spam","eggs","sausages")
你可以使用它们的索引号来访问元组中的值,就像在列表中所进行的那样:
print(words[0])#输出第一个元素
如果试图重新给元组赋值将会产生TypeError ,这也是和列表不同的地方。
words[1]="cheese"
Result:
TypeError:"tuple object dose not support item assignment"
==提示== 和列表以及字典一样,元组可以相互嵌套
列表,字典和元组创建及访问方式的比较
#列表
list=["one","two"]
print(list[0])
#字典
dict={1:"one",2:"two",3:"three"}
print(dict[1])
print(dict.get(2))
#元组
tp=("one","two","three")
print(tp[1])
元组可以在没有括号的情况下创建,可以通过仅仅将值用逗号分开来进行创建。
示例一:
my_tuple="one","two","three"
print(my_tuple[0])
如果要创建一个空的元组,可以使用空括号:
tpl=()
==注意== 元组的访问要快于列表,但是其缺点在于元组不能够被改变
List Slices(列表切片)
列表切片List slices 提供了更加高级的方法从列表中检索值。基本的列表切片包括使用两个逗号隔开的整数来检索列表。这将返回一个新的列表,这个列表包含所有在索引之间的旧列表之间的值。
squares=[0,1,4,9,16,25,36,49,64,81]
print(squares[2:6])
print(squares[3:8])
print(squares[0:1])
Result:
[4,9,16,25]
[9,16,25,64,81]
[0]
==Tips== 和Range 的参数一样,切片提供的第一个所有被包含在结果中,但是第二个并没有被包含在结果中。
如果切片中的第一个数字被省略了,它代表的就是列表的开头。如果第二个数字被删除了,它代表的就是列表的结尾。
示例一:
squares=[0,1,4,9,16,25,36,49,64,81]
print(squares[:7])
print(squares[7:])
Result:
[0,1,4,9,16,25,36]
[49,64,81]
==Tips== 对元组也可以使用切片
列表切片可以有第三个参数,代表的是步数,在切片中只包含备用值:
squares=[0,1,4,9,16,25,36,49,64,81]
print(squares[::2])
print(squares[2:8:3])
Result:
[0,4,16,36,64]
[4,25]
==Tips== 第三个参数的通俗意思就是间隔距离,隔几个数取一个值
负值也可以在列表切片中使用(以及正常的列表索引)。当切片中的第一个和第二个参数被使用负值的时候(或者一个正常的索引),它们将会从列表的末尾开始数起。
squares=[0,1,4,9,16,25,36,49,64,81]
print(squares[1:-1])
Result:
[1,4,16,25,36,49,64]
==Tips== 如果有负值被使用在步骤中,切片将被向后进行切割。使用[::-1]作为一个切片是一个很常见也很惯用的将列表进行倒置的方式,但是如果前面的两个参数存在的话,切片的返回值为[],也就是一个空列表,如果前面两个参数第一个参数比第二个参数大,第三个参数为负值的话,就可以创建一个新的列表。
squares=[0,1,4,9,16,25,64,81]
print(squares[::-1])
print(squares[1:8:-1])
print(squares[::-2])
print(squares[7:1:-2])
Result:
[81,64,49,36,25,16,9,4,1,0]
[]
[81,25,9,1]
[81,25,9]
List Comprehensions(列表解析)
列表解析是一种快速创建列表非常有用的方式,其中列表的内容要遵循简单的规则。例如,我们可以像下面一样进行:
#一个列表解析
cubes=[i**3 for i in range(5)]
print(cubes)
Result:
[0,1,8,27,64]
==Tips== 列表解析的灵感来自于数学中的set-builder计数法,python 计算中,i2* 表示的是积, **i**2 ** 表示的是平方。
列表解析还可以包含if 语句来强制列表中的值的条件。
示例一:
evens=[i**2 for i in range(10) if i**2 % 2 ==0 ]
#下面的代码和上面的代码将会得到同样的结果
evens=[i**2 for i in range(10) if i%2==0]
print(evens)
Result:
[0,4,16,36,64]
如果试图创建一个范围非常极端的列表,将会产生MemoryError ,下面的代码展示的就是列表解析超出了内存的情况:
even=[2*i for i in range(10**100)]
print(even)
Result:
Memory limit exceeded
==Tips== 这个问题可以由生成器来解决,我们将在下一个模块讲解生成器
String Formatting(字符串格式化)
到目前为止,为了字符串和非字符串结合起来,你就得把非字符串转变成字符串然后把它们加在一起。字符串格式化提供了一个更加有效额方式来将非字符串嵌合到字符串中。字符串格式化使用一个字符串的format 方法来替换字符串中的一些参数。
示例一:
# 字符串格式化
nums=[4,5,6]
msg="Numbers:{0}{1}{2}".format(nums[0],nums[1],nums[2])
print(msg)
Result:
Numbers:456
==Tips==
format函数的每个参数都放在字符串中相应的位置,该位置由大括号{}确定。
示例二:
print("{0}{1}{0}.format("abra","cad"))
Result
abracadabra
字符串格式化也可以使用命名参数来完成。
示例一:
a="{x},{y}".format(x=5,y=12)
print(a)
Result:
5,12
Python 包含有大量有用额内置函数和方法来完成相同的任务。
join - 将一个字符串与另外一个作为分隔符的字符串进行连接
replace -将字符串中的一个子字符串替换成另外一个子字符串
startwith和endswith - 分别确定一个子字符串是否在一个字符串的开头或者是否在字符串的末尾。
为了改变字符串的状态,你可以使用lower 和upper 。
split 方法与join 是相反的,将带有特定分隔符的字符串转变为一个列表。
示例一:
print(",".join(["spam","eggs","ham"]))#(1)
print("Hello ME".replace("ME","world"))#(2)
print("This is a sentence".startswith("This"))#(3)
print("This is a sentence".endswith("sentence"))#(4)
print("This is a sentence".upper())#(5)
print("AN ALL CAPS SENTENCE".lower())#(6)
print("spam,eggs,ham".split(","))#(7)
Result:
spam,eggs,ham #(1)
Hello world #(2)
True #(3)
True #(4)
THIS IS A SENTENCE #(5)
an all caps sentence #(6)
['spam', 'eggs', 'ham'] #(7)
数值函数
为了知道一些数字或者列表中最大的或者最小的值,你可以使用max 或者min
为了找到一个数字与零之间的距离(也就是它的绝对值),可以使用 abs
为了把一个小数四舍五入到一定的位置,可以使用round
为了得到整个列表的总和,可以使用sum
示例一:
print(min(1,2,3,4,0,2,1))
print(max(1,4,9,2,5,6,8))
print(abs(-99))
print(abs(42))
print(sum([1,2,3,4,5]))
Result:
0
9
99
42
15
示例二:
a=min([sum([11,22]),max(abs(-30),2)])
print(a)
Result:
a
列表函数
all 和 any 将一个列表作为声明,通常被用在条件语句中,如果all 和 any 中的分别的声明等于True 的话,就返回True ,反之则返回False .
函数enumerate 可以被用来历遍这些值,并创建一个实时列表。
示例一:
nums=[55,44,33,22,11]
if all([i > 5 for i in nums]):
print("All larger than 5")
if any([i % 2 ==0 for i in nums]):
print("At least one is even")
for v in enumerate(nums):
print(V)
Result:
All larger than 5
At least one is even
(0,55)
(1,44)
(2,33)
(3,22)
(4,11)
示例二:
nums=[-1,2,3,4,-5]
if all([abs(i)<3 for i in nums]):
print(1)
else:
print(2)
Result:
2
Text Analyzer(文本分析器)
这是一个示范程序,展示了分析样本文件来找到文本中每个类型的字符所占的百分比是多少的过程。这部分展示了一个文件如何被打开以及被读取。
filename=input("Enter a filaname:")
with open(filename) as f:
text=f.read()
print(text)
这部分的程序展示的计算一个字符在一个字符串中出现了多少次的计算函数。这个函数采用了文件的内容和一个字符作为声明,返回的是该字符在文件中出现的次数。
def count_char(text,char):
count=0
for c in text:
if c==char:
count+=1
return count
filename=input("Enter a filename:")
with.open(filename) as f:
text=f.read()
print(count_char(text,"r"))
==Tips== return 的位置很重要,它和for 循环是同一等级的。
下面的这部分程序是找出文本中每个字符所占的百分比。
示例一:
for char in "abcdhowe hfuwqfohqaou":
perc=100*count_char(text,char)/len(text)
print("{0}-{1}%".foramt(char,round(perc,2)))
下面我们把前面的代码全部放到一起并运行:
def count_char(text,char):
count=0
for c in text:
if c==char:
count+=1
return count
filename=input("Enter a filename:")
with open(filename) as f:
text=f.read()
for char in "dejwo hfowhfowhefoihoKBVKFB":
perc=100*count_char(text,char)/len(text)
print("{0}-{1}%".format(char,round(perc,2)))
示例二:
def count_char(text,char):
count=0
for c in text:
if c==char:
count+=1
return count
text="dhofifbksahfugvlsdhgbvneranak" #随便输的
for char in text:
perc=100*count_char(text,char)/len(text)
print("{0}-{1}-{2}%".format(char,count_char(text,char),round(perc,2)))
print(len(text)) #round函数可以减少小数位数的输出