Python知识点对初学者的解释顺序如何?
我正在给本科数学专业的学生讲Python。我想知道学生学习各种Python概念的最佳顺序。在我看来,每个阶段,学生都应该能用当时掌握的工具解决一些不简单的编程问题。每学到一个新工具,都应该能让他们用更简单的方法解决之前熟悉的问题。为了让学生保持专注,选择Python中众多概念中的一些是很重要的。他们还应该有动力,欣赏每一个新掌握的工具,而不是死记硬背。以下是一些具体的问题:
- 比如,我的前任在讲解字符串之前先讲了列表。我觉得反过来讲更好。
- 函数定义应该在一开始就介绍,还是在掌握基本的结构化编程概念,比如条件判断(if)和循环(while)之后再介绍?
- 集合(sets)应该在字典(dictionaries)之前介绍吗?
- 在课程早期就介绍文件的读写好,还是大部分时间用输入(input)和打印(print)就可以?
欢迎大家提出建议并解释理由。
编辑:在高中时,学生们接触过计算机。其中一些人学会了编程。在此之前,他们上过一门课程,内容包括Word、Excel、PowerPoint、HTML、LaTeX,还有一点Mathematica,但没有编程。五年前,我在这门课程中使用Mathematica,后续课程使用C语言,后来是Java。现在我教Python入门,后续课程我的同事教Python中的面向对象编程。之后,学生们可能会选修数据结构、算法、优化等特别课程,在一些选修课中,他们会自学Mathematica、Matlab和R。
5 个回答
e-satis的建议列表挺不错的,但因为这是数学课,我想再加一些建议:
首先,要么使用Python 3.x,要么告诉他们一定要使用
from __future__ import division
否则,他们会遇到整数除法的问题。比如在交互式提示符下输入1/2时,这个问题很容易记住,但在一些细微的地方就会出现bug,比如:
def mean(seq):
"""Return the arithmetic mean of a list."""
return sum(seq) / len(seq)
在教函数的时候,给他们展示一下数学模块和内置的sum函数。同时也要展示如何把一个函数传递给另一个函数,这对于编写通用的导数/积分近似非常有用:
def derivative(f, x, delta_x=1e-8):
"""Approximate f'(x)."""
return (f(x + delta_x) - f(x - delta_x)) / (2 * delta_x)
print(derivative(math.sin, 0))
你可以在这里查看我的大纲:http://homepage.mac.com/s_lott/books/nonprog/html/index.html
这个演示的顺序是根据我教C语言、Ada、C++、PL/SQL(甚至还教过一次COBOL课程)的经验来安排的。
有一本很棒的书,里面的概念排列得很合理,适合教学。
书名是《与操作系统应用的结构化并发编程》,作者是R. C. Holt、G. S. Graham、E. D. Lazowska和M. A. Scott,出版于1978年,由Addison-Wesley出版,ISBN是0201029375。
作为一名老师,经过一些尝试和错误,我决定采用以下方法:
(从零开始,根据他们的水平调整)
- 简单介绍一下Python是什么,以及你可以用它做什么。跳过那些技术性的说辞,专注于他们想做的事情:音乐、图形界面、网站、重命名文件等等。
- 安装Python,运行解释器。如果可以的话,使用 iPython。
- 变量、基本字符串和
print()
。 - 整数和数据类型(包括类型错误和类型转换)。
- 基本的数学运算。给他们看
1 / 0
和10 / 3
,但不要纠结细节。 - 把计算结果放入变量中。
- 在计算中使用变量。
- 用
%
进行字符串格式化。只展示 "%s",这就足够了,并且总是有效。即使只有一个项目,也要始终使用一个元组(以逗号结尾)。 - 列表、索引、切片和常见错误。然后展示元组作为“冻结”的列表(以及类型转换)。展示它们可以相互包含。让他们在这方面练习,直到完全掌握:这非常非常重要。
- 字典,包含常见错误。与元组和列表的嵌套。强调最后一点。
- 对字符串、列表、元组和字典进行
for
循环。 - 对嵌套类型进行
for
循环。要有耐心,慢慢来。掌握这一部分会改变一切。 - 字典的
items()
、values()
和keys()
。 - 使用
for
读取文件,包括IOErrors
。 - 写入文件。
- 使用方法。用字符串作为例子,展示
strip()
、lower()
、split()
等等。不要解释面向对象编程(OOP),只讲如何使用方法。从现在开始多用“方法”这个词。 - 创建一个模块文件并使用它。只创建一个模块,所有内容都放在里面。
- 函数(只用
return
,不使用print()
。禁止在函数中使用print()
。) - 函数参数。
- 命名参数。
- 默认值参数。
try
/except
和异常处理。import
和创建你自己的目录模块。展示所有特殊情况(解释这些需要的时间比你想象的要多得多)。- 演示一些标准模块(但不要花太多时间在这上面,这只是为了展示):datetime、string、os 和 sys。避免抽象的东西,比如 itertools,它们是程序员的梦想,但对学生来说却是噩梦。
之后你可以引入面向对象编程,但这会复杂一些。用字符串、列表和文件来介绍对象的概念。当他们理解后,再开始讲类。愿力量与你同在 :-)
在函数中使用 print
来展示如何工作是很诱人的,使用 raw_input
更是如此。你应该尽量避免这样做。 第一个会让“返回值”的概念变得很难理解,第二个则会掩盖程序的真实流程,学生很难理解你需要将函数串联起来,而不是每次都询问用户所需的每个值。
一般来说,选择一种有效的方法并坚持使用。不要展示替代方案。例如:
只展示使用 %
进行字符串格式化,忽略 +
和 ,
。你可以在讲义中添加一个“深入了解”的小块,供想了解更多的人参考。只展示 for
,而不展示 while
。你几乎可以用 for
编写90%的Python程序,而不需要 while
。避免使用 +=
。不要展示如何用整数乘以字符串/列表/字典。虽然这并不错误,但会导致他们产生误解。你需要让他们专注于主要概念。
不要展示集合。集合非常有用,但很少使用。鼓励他们在家编程,如果遇到问题就问你。在这种情况下,如果集合是解决方案,再展示它们。了解集合需要时间和学生的脑力资源,这些资源可以用来学习更常用的东西。他们将有足够的时间在以后学习新工具,而不需要你:专注于那些难以或耗时学习的内容。
同样,enumerate
也是如此。拥有C或Java背景的学生会使用索引来循环,而不是使用 for
,如果你给他们 enumerate
。出于类似的原因,将 len
、fd.read
、fd.readlines
和 range
留到最后的课程中,称为“高级Python”,如果你有时间的话。
甚至不要考虑生成器、元类和装饰器。这些概念只有极少数学生能理解,即使经过几个月的练习。 列表推导、with
和三元运算符可以在最后几节课中引入,如果你觉得你的学生很聪明。
最后,随意强化良好的编程习惯。PEP8格式、良好的架构、命名约定、没有不可变的默认参数等等。他们现在无法了解这些。不要担心,你是老师,你有权偶尔说“这就是事实”。
哦,如果他们不从学习字节码、递归、汇编、复杂度、冒泡排序、栈、实现细节等开始,他们会成为更好的程序员。教一个无法编写出体面Python程序的人这些内容是浪费时间,他根本无法理解这些是什么。实践是将理论带入的最佳工具。再说一次,如果你正确地准备他们,他们会在以后自己学习其他所有内容,所以优先考虑,别害怕跳过概念,即使是简单或重要的概念。