如果只能选择一本Python书入门,那我选这本

什么是编程

在电视剧和电影中,常常看到程序员在闪光的屏幕上迅速地输入密码般的一串1和0,但现代编程没有这么神秘。编程只是输入指令让计算机来执行。这些指令可能运算一些数字,修改文本,在文件中查找信息,或通过因特网与其他计算机通信。

所有程序都使用基本指令作为构件块。下面是一些常用的指令,用自然语言的形式来表示:

“做这个,然后做那个。”

“如果这个条件为真,执行这个动作,否则,执行那个动作。”

“按照指定次数执行这个动作。”

“一直做这个,直到条件为真。”

也可以组合这些构件块,实现更复杂的决定。例如,这里有一些编程指令,称为源代码,是用Python编程语言编写的一个简单程序。从头开始,Python软件执行每行代码(有些代码只有在特定条件为真时执行,否则Python会执行另外一些代码),直到到达底部。

❶ passwordFile = open('SecretPasswordFile.txt')
❷ secretPassword = passwordFile.read()
❸ print('Enter your password.')
typedPassword = input()
❹ if typedPassword == secretPassword:
❺     print('Access granted')
❻     if typedPassword == '12345':
❼         print('That password is one that an idiot puts on their luggage.')
else:
❽     print('Access denied')

你可能对编程一无所知,但读了上面的代码,也许就能够合理地猜测它做的事。首先,打开了文件SecretPasswordFile.txt❶,读取了其中的密码❷。然后,提示用户(通过键盘)输入一个密码❸。比较这两个密码❹,如果它们一样,程序就在屏幕上打印Access granted❺。接下来,程序检查密码是否为12345❻,提示说这可能并不是最好的密码❼。如果密码不一样,程序就在屏幕上打印Access denied❽。

什么是Python

Python指的是Python编程语言(包括语法规则,用于编写被认为是有效的Python代码),以及Python解释器软件,它读取源代码(用python语言编写),并执行其中的指令。Python解释器可以从http://python.org/免费下载,有针对Linux、OS X和Windows的版本。

Python的名字来自于英国超现实主义喜剧团体,而不是来自于蛇。Python程序员被亲切地称为Pythonistas。Monty Python和与蛇相关的引用常常出现在Python的指南和文档中。

程序员不需要知道太多数学

我听到的关于学习编程的最常见的顾虑,就是人们认为这需要很多数学知识。其实,大多数编程需要的数学知识不超过基本算数。实际上,善于编程与善于解决数独问题没有太大差别。

要解决数独问题,数字1到9必须填入9×9的棋盘上每一行、每一列,以及每个3×3的内部方块。通过推导和起始数字的逻辑,你会找到一个答案。例如,在图 1的数独问题中,既然5出现在了左上角,它就不能出现在顶行、最左列,或左上角3×3方块中的其他位置。每次解决一行、一列或一个方块,将为剩下的部分提供更多的数字线索。

仅仅因为数独使用了数字,并不意味着必须精通数学才能求出答案。编程也是这样。就像解决数独问题一样,编程需要将一个问题分解为单个的、详细的步骤。类似地,在调试程序时(即寻找和修复错误),你会耐心地观察程序在做什么,找出缺陷的原因。像所有技能一样,编程越多,你就掌握得越好。

图1 一个新的数独问题(左边)及其答案(右边)。尽管使用了数字,数独并不需要太多数学知识

Python编程语言有许多语法结构、标准库函数和交互式开发环境功能。好在,你可以忽略大多数内容。你只需要学习部分内容,就能编写一些方便的小程序。

但在动手之前,你必须学习一些基本编程概念。就像魔法师培训,你可能认为这些概念既深奥又啰嗦,但有了一些知识和实践,你就能像魔法师一样指挥你的计算机,完成难以置信的事情。

市场上Python入门书很多,如果只让我推荐一本的话,我会选择这本:《Python编程快速上手 让繁琐工作自动化》

从这本书里你能学到什么?

本书的第一部分介绍了基本Python编程概念,第二部分介绍了一些不同的任务,你可以让计算机自动完成它们。第二部分的每一章都有一些项目程序,供你学习。下面简单介绍一下每章的内容。

第一部分:Python编程基础

“第 1 章:Python基础”介绍了表达式、Python指令的最基本类型,以及如何使用Python交互式环境来尝试运行代码。

“第 2 章:控制流”解释了如何让程序决定执行哪些指令,以便代码能够智能地响应不同的情况。

“第3章:函数”介绍了如何定义自己的函数,以便将代码组织成可管理的部分。

“第4章:列表”介绍了列表数据类型,解释了如何组织数据。

“第 5 章:字典和结构化数据”介绍了字典数据类型,展示了更强大的数据组织方法。

“第6章:字符串操作”介绍了处理文本数据(在Python中称为字符串)。

第二部分:自动化任务

“第7章:模式匹配与正则表达式”介绍了Python如何用正则表达式处理字符串,以及查找文本模式。

“第 8 章:读写文件”解释了程序如何读取文本文件的内容,并将信息保存到硬盘的文件中。

“第 9 章:组织文件”展示了Python如何用比手工操作快得多的速度,复制、移动、重命名和删除大量的文件,也解释了压缩和解压缩文件。

“第10章:调试”展示了如何使用Python的缺陷查找和缺陷修复工具。

“第 11 章:从Web抓取信息”展示了如何编程来自动下载网页,解析它们,获取信息。这称为从Web抓取信息。

“第 12 章:处理Excel电子表格”介绍了编程处理Excel电子表格,这样你就不必去阅读它们。如果你必须分析成百上千的文档,这是很有帮助的。

“第13章:处理PDF和Word文档”介绍了编程读取Word和PDF文档。

“第14章:处理CSV文件和JSON数据”解释了如何编程操作CSV和JSON文件。

“第15章:保持时间、计划任务和启动程序”解释了Python程序如何处理时间和日期,如何安排计算机在特定时间执行任务。这一章也展示了Python程序如何启动非Python程序。

“第16章:发送电子邮件和短信”解释了如何编程来发送电子邮件和短信。

“第17章:操作图像”解释了如何编程来操作JPG或PNG这样的图像。

“第18章:用GUI自动化控制键盘和鼠标”解释了如何编程控制鼠标和键盘,自动化鼠标点击和击键。

本书的读者对象

软件是我们今天使用的许多工具的核心:几乎每个人都使用社交网络来进行交流,许多人的手机中都有连接因特网的计算机,大多数办公室工作都涉及操作计算机来完成工作。因此,对编程人才的需求暴涨。无数的图书、交互式网络教程和开发者新兵训练营,承诺将有雄心壮志的初学者变成软件工程师,获得6位数的薪水。

本书不是针对这些人的。它是针对所有其他的人。

就它本身来说,这本书不会让你变成一个职业软件开发者,就像几节吉他课程不会让你变成一名摇滚巨星。但如果你是办公室职员、管理者、学术研究者,或使用计算机来工作或娱乐的任何人,你将学到编程的基本知识,这样就能将下面这样一些简单的任务自动化:

  • 移动并重命名几千个文件,将它们分类,放入文件夹;
  • 填写在线表单,不需要打字;
  • 在网站更新时,从网站下载文件或复制文本;
  • 让计算机向客户发出短信通知;
  • 更新或格式化Excel电子表格;
  • 检查电子邮件并发出预先写好的回复。

对人来说,这些任务简单,但很花时间。它们通常很琐碎、很特殊,没有现成的软件可以完成。有一点编程知识,就可以让计算机为你完成这些任务。

样章试读:第5章 字典和结构化数据

在本章中,我将介绍字典数据类型,它提供了一种灵活的访问和组织数据的方式。然后,结合字典与前一章中关于列表的知识,你将学习如何创建一个数据结构,对井字棋盘建模。

5.1 字典数据类型

像列表一样,“字典”是许多值的集合。但不像列表的下标,字典的索引可以使用许多不同数据类型,不只是整数。字典的索引被称为“键”,键及其关联的值称为“键-值”对。

在代码中,字典输入时带花括号{}。在交互式环境中输入以下代码:

>>> myCat = {'size': 'fat', 'color': 'gray', 'disposition': 'loud'}

这将一个字典赋给myCat变量。这个字典的键是'size'、'color'和'disposition'。这些键相应的值是'fat'、'gray'和'loud'。可以通过它们的键访问这些值:

>>> myCat['size']
'fat'
>>> 'My cat has ' + myCat['color'] + ' fur.'
'My cat has gray fur.'

字典仍然可以用整数值作为键,就像列表使用整数值作为下标一样,但它们不必从0开始,可以是任何数字。

>>> spam = {12345: 'Luggage Combination', 42: 'The Answer'}

5.1.1 字典与列表

不像列表,字典中的表项是不排序的。名为spam的列表中,第一个表项是spam[0]。但字典中没有“第一个”表项。虽然确定两个列表是否相同时,表项的顺序很重要,但在字典中,键-值对输入的顺序并不重要。在交互式环境中输入以下代码:

>>> spam = ['cats', 'dogs', 'moose']
>>> bacon = ['dogs', 'moose', 'cats']
>>> spam == bacon
False
>>> eggs = {'name': 'Zophie', 'species': 'cat', 'age': '8'}
>>> ham = {'species': 'cat', 'age': '8', 'name': 'Zophie'}
>>> eggs == ham
True

因为字典是不排序的,所以不能像列表那样切片。

尝试访问字典中不存在的键,将导致KeyError出错信息。这很像列表的“越界”IndexError出错信息。在交互式环境中输入以下代码,并注意显示的出错信息,因为没有'color'键:

>>> spam = {'name': 'Zophie', 'age': 7}
>>> spam['color']
Traceback (most recent call last):
  File "", line 1, in 
    spam['color']
KeyError: 'color'

尽管字典是不排序的,但可以用任意值作为键,这一点让你能够用强大的方式来组织数据。假定你希望程序保存朋友生日的数据,就可以使用一个字典,用名字作为键,用生日作为值。打开一个新的文件编辑窗口,输入以下代码,并保存为birthdays.py:

❶ birthdays = {'Alice': 'Apr 1', 'Bob': 'Dec 12', 'Carol': 'Mar 4'}

 while True:
     print('Enter a name: (blank to quit)')
     name = input()
     if name == '':
         break

❷     if name in birthdays:
❸         print(birthdays[name] + ' is the birthday of ' + name)
     else:
         print('I do not have birthday information for ' + name)
         print('What is their birthday?')
         bday = input()
❹         birthdays[name] = bday
         print('Birthday database updated.')

你创建了一个初始的字典,将它保存在birthdays中❶。用in关键字,可以看看输入的名字是否作为键存在于字典中❷,就像查看列表一样。如果该名字在字典中,你可以用方括号访问关联的值❸。如果不在,你可以用同样的方括号语法和赋值操作符添加它❹。

运行这个程序,结果看起来如下所示:

Enter a name: (blank to quit)
Alice
Apr 1 is the birthday of Alice
Enter a name: (blank to quit)
Eve
I do not have birthday information for Eve
What is their birthday?
Dec 5
Birthday database updated.
Enter a name: (blank to quit)
Eve
Dec 5 is the birthday of Eve
Enter a name: (blank to quit)

当然,在程序终止时,你在这个程序中输入的所有数据都丢失了。在第 8章中,你将学习如何将数据保存在硬盘的文件中。

5.1.2 keys()、values()和items()方法

有3个字典方法,它们将返回类似列表的值,分别对应于字典的键、值和键-值对:keys()、values()和items()。这些方法返回的值不是真正的列表,它们不能被修改,没有append()方法。但这些数据类型(分别是dict_keys、dict_values和dict_items)可以用于for循环。为了看看这些方法的工作原理,请在交互式环境中输入以下代码:

>>> spam = {'color': 'red', 'age': 42}
>>> for v in spam.values():
        print(v)
 
red
42

这里,for循环迭代了spam字典中的每个值。for循环也可以迭代每个键,或者键-值对:

>>> for k in spam.keys():
        print(k)
 
color
age
>>> for i in spam.items():
        print(i)
 
('color', 'red')
('age', 42)

利用keys()、values()和items()方法,循环分别可以迭代键、值或键-值对。请注意,items()方法返回的dict_items值中,包含的是键和值的元组。

如果希望通过这些方法得到一个真正的列表,就把类似列表的返回值传递给 list函数。在交互式环境中输入以下代码:

>>> spam = {'color': 'red', 'age': 42}
>>> spam.keys()
dict_keys(['color', 'age'])
>>> list(spam.keys())
['color', 'age']

list(spam.keys())代码行接受keys()函数返回的dict_keys值,并传递给list()。然后返回一个列表,即['color', 'age']。

也可以利用多重赋值的技巧,在for循环中将键和值赋给不同的变量。在交互式环境中输入以下代码:

>>> spam = {'color': 'red', 'age': 42}
>>> for k, v in spam.items():
        print('Key: ' + k + ' Value: ' + str(v))
 
Key: age Value: 42
Key: color Value: red

5.1.3 检查字典中是否存在键或值

回忆一下,前一章提到,in和not in操作符可以检查值是否存在于列表中。也可以利用这些操作符,检查某个键或值是否存在于字典中。在交互式环境中输入以下代码:

>>> spam = {'name': 'Zophie', 'age': 7}
>>> 'name' in spam.keys()
True
>>> 'Zophie' in spam.values()
True
>>> 'color' in spam.keys()
False
>>> 'color' not in spam.keys()
True
>>> 'color' in spam
False

请注意,在前面的例子中,'color' in spam本质上是一个简写版本。相当于'color' in spam.keys()。这种情况总是对的:如果想要检查一个值是否为字典中的键,就可以用关键字in(或not in),作用于该字典本身。

5.1.4 get()方法

在访问一个键的值之前,检查该键是否存在于字典中,这很麻烦。好在,字典有一个get()方法,它有两个参数:要取得其值的键,以及如果该键不存在时,返回的备用值。

在交互式环境中输入以下代码:

>>> picnicItems = {'apples': 5, 'cups': 2}
>>> 'I am bringing ' + str(picnicItems.get('cups', 0)) + ' cups.'
'I am bringing 2 cups.'
>>> 'I am bringing ' + str(picnicItems.get('eggs', 0)) + ' eggs.'
'I am bringing 0 eggs.'

因为picnicItems字典中没有'egg'键,get()方法返回的默认值是0。不使用get(),代码就会产生一个错误消息,就像下面的例子:

>>> picnicItems = {'apples': 5, 'cups': 2}
>>> 'I am bringing ' + str(picnicItems['eggs']) + ' eggs.'
Traceback (most recent call last):
  File "<pyshell#34>", line 1, in 
    'I am bringing ' + str(picnicItems['eggs']) + ' eggs.'
KeyError: 'eggs'

5.1.5 setdefault()方法

你常常需要为字典中某个键设置一个默认值,当该键没有任何值时使用它。代码看起来像这样:

spam = {'name': 'Pooka', 'age': 5}
if 'color' not in spam:
    spam['color'] = 'black'

setdefault()方法提供了一种方式,在一行中完成这件事。传递给该方法的第一个参数,是要检查的键。第二个参数,是如果该键不存在时要设置的值。如果该键确实存在,方法就会返回键的值。在交互式环境中输入以下代码:

>>> spam = {'name': 'Pooka', 'age': 5}
>>> spam.setdefault('color', 'black')
'black'
>>> spam
{'color': 'black', 'age': 5, 'name': 'Pooka'}
>>> spam.setdefault('color', 'white')
'black'
>>> spam
{'color': 'black', 'age': 5, 'name': 'Pooka'}

第一次调用setdefault()时,spam变量中的字典变为{'color': 'black', 'age': 5, 'name': 'Pooka'}。该方法返回值'black',因为现在该值被赋给键'color'。当spam.setdefault('color', 'white')接下来被调用时,该键的值“没有”被改变成'white',因为spam变量已经有名为'color'的键。

setdefault()方法是一个很好的快捷方式,可以确保一个键存在。下面有一个小程序,计算一个字符串中每个字符出现的次数。打开一个文件编辑器窗口,输入以下代码,保存为characterCount.py:

message = 'It was a bright cold day in April, and the clocks were striking thirteen.'
count = {}

for character in message:
    count.setdefault(character, 0)
    count[character] = count[character] + 1

print(count)

程序循环迭代message字符串中的每个字符,计算每个字符出现的次数。setdefault()方法调用确保了键存在于count字典中(默认值是0),这样在执行count[character] = count[character] + 1时,就不会抛出KeyError错误。程序运行时,输出如下:

{' ': 13, ',': 1, '.': 1, 'A': 1, 'I': 1, 'a': 4, 'c': 3, 'b': 1, 'e': 5, 'd': 3, 'g': 2, 'i':
6, 'h': 3, 'k': 2, 'l': 3, 'o': 2, 'n': 4, 'p': 1, 's': 3, 'r': 5, 't': 6, 'w': 2, 'y': 1}

从输出可以看到,小写字母c出现了3次,空格字符出现了13次,大写字母A出现了1次。无论message变量中包含什么样的字符串,这个程序都能工作,即使该字符串有上百万的字符!

5.2 漂亮打印

如果程序中导入pprint模块,就可以使用pprint()和pformat()函数,它们将“漂亮打印”一个字典的字。如果想要字典中表项的显示比print()的输出结果更干净,这就有用了。修改前面的characterCount.py程序,将它保存为prettyCharacterCount.py。

import pprint
message = 'It was a bright cold day in April, and the clocks were striking
thirteen.'
count = {}

for character in message:
    count.setdefault(character, 0)
    count[character] = count[character] + 1

pprint.pprint(count)

这一次,当程序运行时,输出看起来更干净,键排过序。

{' ': 13,
 ',': 1,
 '.': 1,
 'A': 1,
 'I': 1,
 'a': 4,
 'b': 1,
 'c': 3,
 'd': 3,
 'e': 5,
 'g': 2,
 'h': 3,
 'i': 6,
 'k': 2,
 'l': 3,
 'n': 4,
 'o': 2,
 'p': 1,
 'r': 5,
 's': 3,
 't': 6,
 'w': 2,
 'y': 1}

如果字典本身包含嵌套的列表或字典,pprint.pprint()函数就特别有用。

如果希望得到漂亮打印的文本作为字符串,而不是显示在屏幕上,那就调用pprint.pformat()。下面两行代码是等价的:

pprint.pprint(someDictionaryValue)
print(pprint.pformat(someDictionaryValue))

5.3 使用数据结构对真实世界建模

甚至在因特网之前,人们也有办法与世界另一边的某人下一盘国际象棋。每个棋手在自己家里放好一个棋盘,然后轮流向对方寄出明信片,描述每一着棋。要做到这一点,棋手需要一种方法,无二义地描述棋盘的状态,以及他们的着法。

在“代数记谱法”中,棋盘空间由一个数字和字母坐标确定,如图5-1所示。

图5-1 代数记谱法中棋盘的坐标

棋子用字母表示:K表示王,Q表示后,R表示车,B表示象,N表示马。描述一次移动,用棋子的字母和它的目的地坐标。一对这样的移动表示一个回合(白方先下),例如,棋谱2. Nf3 Nc6表明在棋局的第二回合,白方将马移动到f3,黑方将马移动到c6。

代数记谱法还有更多内容,但要点是你可以用它无二义地描述象棋游戏,不需要站在棋盘前。你的对手甚至可以在世界的另一边!实际上,如果你的记忆力很好,甚至不需要物理的棋具:只需要阅读寄来的棋子移动,更新心里想的棋盘。

计算机有很好的记忆力。现在计算机上的程序,很容易存储几百万个像'2. Nf3 Nc6'这样的字符串。这就是为什么计算机不用物理棋盘就能下象棋。它们用数据建模来表示棋盘,你可以编写代码来使用这个模型。

这里就可以用到列表和字典。可以用它们对真实世界建模,例如棋盘。作为第一个例子,我们将使用比国际象棋简单一点的游戏:井字棋。

发布了556 篇原创文章 · 获赞 298 · 访问量 90万+

猜你喜欢

转载自blog.csdn.net/epubit17/article/details/104939174
今日推荐