第一章 程序设计的基本方法

计算机的概念

  • 计算机是根据指令操作数据的设备,具备功能性和可编辑性的两个基本特性。
  • 功能性:对数据的操作,表现为对数据计算,输入输出处理和结果存储等
  • 可编程性:根据一系列指令自动地,可预测的,准确地完成操作者的意图。
  • 拓展:摩尔定律:单位面积集成电路上可容纳晶体管的数量约每两年翻一倍。
  • 计算机技术的演进过程:①计算机系统结构阶段②计算机网络和视窗阶段③复杂信息系统阶段④人工智能阶段
  • 列出5个你所了解的近十年出现的计算机技术名词:区块链(Blockchain):一种分布式数据库技术,通 过去中心化的方式来管理和维护交易数据,实现 信息共享和透明化。 云计算(Cloud Computing):一种基于互联网的计 算方式,通过将计算和存储资源集中在云端,提 供按需使用、弹性伸缩、易于管理的计算服务。 物联网(Internet of Things,IoT):将传感器、 网络、计算和分析技术等融合起来,实现对物理 世界的实时监测、数据采集和智能控制的技术。 虚拟现实(Virtual Reality,VR):通过计算机技 术实现人机交互和仿真的技术,使用户可以身临 其境地感受到虚拟场景中的视觉、听觉和触觉等 感觉。人工智能(AI):指的是通过智能算法和模型模拟 人类的思维和行为,并实现自主学习和适应的能 力的技术。
  • 简述预测评估的三种方法:外推预测,理论预测,判断预测。

程序设计语言

  • 机器语言:二进制语言。 汇编语言:助记符和计算机指令一一对应。高级语言:接近自然语言的一种计算机程序设计语言。
  • 计算机执行源程序的两种方式:编译和解释。
    • 编译:将源代码一次性转换成目标代码的过程。(一次性翻译,不需要源代码)(类似英文翻译
    • 解释:将源代码逐条转换成目标代码同时逐条运行的过程。(类似同声传译)
  • 静态语言和脚本语言:
    • 静态语言:采用编译执行的编程语言。编译器一次性生成目标代码,,优化更充分,程序运行速度更快。
    • 动态语言:采用解释执行的编程语言。执行程序时需要源代码,维护更灵活。跨多个操作系统平台。
计算机编程
  • CPU可以直接理解的程序设计语言是机器语言
  • 简述编译和解释两种执行方式的区别和各自的缺点:编译:一次性翻译,之后不再需要源代码(类似英文翻译) 解释:每次程序运行时随翻译随执行(类似实时的同声传 译)
  • 列出三个学习编程语言的理由:编程能够训练思维,增进认识,带来乐趣,提高效率,提供就业机会。

Python语言概述

Python语言是一个语法简洁,跨平台,可扩展的开源通用脚本语言。

  • 扩展:开源软件:开放源代码软件的统称。
  • 编写hello world:>>>是Python语言运行环境的提示符。
  • Python语言的特点:语法简洁,与平台无关,粘性扩展,开源理念,通用灵活,强制可读(强制缩进),支持中文,模式多样,类库丰富。

练习

  • 列出不少于3个开源软件的意义:①降低学习成本②有利于程序演进③推动了互联网的进步。

Python语言开发环境配置

IDLE是一个轻量级的Python语言开发环境,可以支持交互式和批量式两种编程方式。

  • Python安装包安装的最重要的两个程序是Python命令行和Python集成开发环境。

  • 运行Python的两种方式:交互式和文件式。

    • 交互式:Python解释器即时响应用户输入的每条代码,给出输出结果。
    • 文件式:(批量式)用户将Python程序写在一个或多个文件中,然后启动Python解释器批量执行文件中的代码。
    • 交互式用于调试少量的代码,文件式最常用。
    • 交互式的启动和运行方法:①Windows系统安装目录,在控制台输入Python 输入exit() 或quit()时可以推出Python运行环境②调用IDLE
    • 文件式的启动和运行方法:①打开cmd的命令行,保存为.py的文件②打开IDLE按快捷键Ctrl+N打开一个新窗口,或者选择file-new file创建新窗口。运行文件:F5或者run-run module
  • 运行Python小程序

    斐波那契数列每个数是前两个数之和。

    练习

    两个连续的print()函数输出内容一般会分行显示,即调用 print()函数后会换行并结束当前行,如何让两个print)函数 的输出打印在一行内? 在print()参数列表中添加end=“”,表示以空字符结尾,替换 默认的换行结尾。

    Python中获取日期和时间的库有datetime time

程序的基本编写方法

IPO程序编写方法
  • INPUT输入
    • 文件输入
    • 网络输入:使用互联网上的数据。明确网络协议和固定的网络接口。
    • 控制台输入:程序使用者所输入的信息。
    • 交互界面输入:例如鼠标移动,单击/双击,文本框内的键盘操作。
    • 随机数据输入:使用随机数生成程序或者调用相关函数。
    • 内部参数输入:以程序内部定义的初始化变量为输入。
  • OUTPUT输出
    • 控制台输出:以计算机屏幕为输出目标,通过程序运行环境的命令行打印输出结果。
    • 图形输出:高级人机交互方法
    • 网络输出:以访问网络接口输出数据
    • 文件输出:以生成新的文件或修改已有文件方式输出运行结果
    • 操作系统内部变量输出:指程序将运行结果输出到系统内部变量中,这类变量包括管道,线程,信号量等。
  • PROCESS处理
    • (算法)
  • 问题的计算部分
    • 分析问题:分析问题的计算部分,想清楚
    • 划分边界:划分问题的功能边界,规划IPO
    • 设计算法:设计问题的求解算法,关注算法
    • 编写程序:编写程序的计算程序
    • 调试测试:调试程序使正确运行,更新完善
    • 升级维护:适应问题的升级维护,更新完善

练习

  • 测试一台机器是否真正拥有人的智能,用IPO描述(参考图灵测试)

Input: 给出一个问题及回答者的答案

Process: 将回答者答案与人类答案进行比较

Output: 回答者是人或计算机

  • 解决问题的过程中,哪些步骤可能用到Python语言?Python 语言能够帮助求解问题中的计算部分。
  • 调试和测试有什么区别和联系:

调试指排除程序错误,此时程序输出是不正确的。测试指在程序正确输出后对其他特性诸如性能,安全性进行进一步探究和改进,此时程序的输出是正确的。

Python语言的版本更迭

  • 更高级别的3。0系列不兼容早期的2。0系列
    • 修改编码UTF-8不需要在前面增加u
    • 使用print()函数代替语句
    • 修改exec()函数
    • 不用《》用≠
    • 比较两个元素的时候,如果两个元素间不存在有意义的顺序关系,将抛出TypeError错误
    • 去掉长整数类型,只有int类型无范围限制
    • 修改整数除法(/)返回浮点数 (//)返回整数
    • 修改八进制整数格式,0o开头
    • 增加关键字:as,with,true,false,none
    • 修改range()函数,不返回列表,返回列表需要通过list()函数转换。
    • 使用关键字as的异常信息
>>>try:
... wrong_name
...except NameError,err:
... print err
...

练习

  • Python 2 输出是 print “祖国,你好”,Python 3 输出是 print(“祖国,你好”)。

[1.18]: Python 2 中的 input()返回类型取决于输入类型,Python 3 中无论输入什么,input()返

回的都是字符串

  • 如何快速判断一个代码是Python3.0版本

: (1) 观察它们的 print 用法

(2) 代码中有 from future import xxxxxx,一定是 2.x;

(3) 代码中有中文变量名,一定是 3.x。

程序练习题
  • 连接两个字符串:format(str1,str2)
  • 从1到N求和

for i in range(int(n)):

sum+=i+1

  • 注意for循环后面是要加上冒号的

第二章 Python程序实例解析

温度转换

  • 分析问题:直接将温度值进行转换,前后都需要给出温度体系
  • 划分边界:输入,处理,输出和格式设计
  • 算法:完成特定计算的一组有序操作
C=(F-32)/1.8
F=C*1.8+32
  • 编写程序
TempStr=input("请输入带有符号的温度值:")
if TempStr[-1]in['F','f']:
  c=(eval(TempStr[0:-1])-32)/1.8
  print("转换后的温度是:{:.2f}C".format(C))
elif TempStr[-1]in['C','c']:
    F=1.8*eval(TempStr[0:-1])+32
    print("转换后的温度是:{:.2f}F".format(F))
else:
    print("输入格式错误")

  • 升级维护:根据应用场景等因素进行维护和升级
  • format是Python中用于格式化字符串的方法。它可以将变量或常量插入到字符串中,并按照指定的格式进行输出。使用format方法可以使代码更加简洁和易读。

练习

  • 用计算机进行财务统计和报表分析

(1) 收支记录:公司所有部门的收支记录采用计算机录入并管理;

(2) 分析比较:对收支历史数据进行比较分析;

(3) 财务审计:计算机辅助找到财务漏洞。

  • 哪种类型的问题没办法通过程序设计来解决

模糊或主观性很强的问题、鉴赏类问题、纠纷类问题等。

Python程序语法元素分析

程序的格式框架
  • 缩进:每行代码之前的包含和层次关系。长度一致:一般用四个空格或一个tab

功能:①表示层次②嵌套

一般来说,判断,循环,函数,类等简单的语法形式能够通过缩进包含一批代码

注释
  • 用于提高代码可读性的辅助性的文字,不被执行。
  • 注释方法
    • 单行注释:以#开头
    • 多行注释:以··· 开头和结尾(三个单引号)
变量

用来保存和表示数据的占位符号

使用等号=表示对变量进行赋值和修改值

命名与保留字
  • 命名

    • 大写字母,小写字母,数字,下划线,汉字
    • 大小写敏感,首字符不能是数字,不与保留字相同 如果允许变量名开头是数字,则无法区分变量名和数字类型
  • 保留字

    • 关键字,内部定义并保留使用的标志符
    • Python中有33个保留字 if,elif,else,in

    外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

    • 注意:保留字是编程语言的基本单词,大小写敏感。
  • 数据类型

    • 字符串,整数,浮点数,列表
    • 如10,011,101既可以看做一段数字,又可以看做一段包括逗号的文本,所以文本符要用双引号括起来,列表类型用中括号括起来
    • 列表类型用in来判断一个元素是否在列表中
字符串
  • 有0个或多个字符组成的有效字符序列,用一对双引号或单引号表示
  • 字符串的序号:正向递增序号从0开始,反向递减序号从-1开始
  • 使用:返回字符串的n个字符,<字符串>[M] 返回字符串的一段字符<字符串>[M:N]
赋值语句
  • 有赋值符号构成的一段代码,赋值语句右侧的数据类型同时作用于变量
  • 同步赋值,x,y=y,x 表示交换x和y的值,将右侧表达式的值一次赋值给左侧变量
  • input函数 <变量> =input(<提示性文字>)
    • 无论用户输入的是字符或数字,input函数统一按照字符串类型输出
分支语句

有判断条件决定程序运行方向的语句

  • 使用方式:
if<条件1>:
    语句
elif<条件2>:
    语句
else:
    语句
  • 保留字后条件为真。执行冒号后面的 语句
  • 冒号后面采用缩进表示后续语句和条件的所属关系
输出函数print()
  • print(<拟输出字符串或字符串变量>)
  • 输出变量值的时候采用格式化输出的格式
    • print(“转换后的温度是{:.2f}C.format©)
    • {}表示槽,后续的变量填充到槽中,里面的内容表示控制格式
评估函数eval()
  • 将输入的字符串转化为Python内部可以进行数学运算的Python语句
  • 使用eval处理字符串,左右两边有三个单引号
  • 如果想要输入一个数字,并对数字进行计算,,eval(input(提示输入字符串))
循环语句

表达式为真时,执行语句块1,表达式为假时执行语句块2。如果有保留字not表示取反。

Python蟒蛇绘制

import turtle as t
t.setup(650,350,200,200)#设置画框
t.penup()
t.fd(-250)
t.pendown()#把画笔移动到画框的最左侧
t.pensize(25)#设置画笔的大小
t.pencolor("purple")#设置画笔的颜色
t.seth(-40)#先转动40度
for i in range(4):
    t.circle(40,80)
    t.circle(-40,80)#共4个上下循环
t.circle(40,80/2)#再向下转动一点,优化一下过渡
t.fd(40)
t.circle(16,180)#回转蛇头
t.fd(40*2/3)#蛇头前进一点距离

  • 拓展:面向对象编程。基于对象的编程范式。对象是事物的一种抽象,他是一个实体,包含属性和方法两部分。属性是对象中的变量,方法是对象能够完成的操作。
  • 引用函数库的方式:import《库名》
    • from <库名> import <函数名,函数名>
    • from<库名> import *
    • 使用这两种方式调用的库函数不用使用库名,直接使用函数名和函数参数。
    • 可能会产生函数重名的问题:解释器在函数的对照表中取出最靠前的函数,可以对函数取小名
  • for循环比一行一行的代码多一次为下一次循环做准备的过程(转向)。

turtle库语法元素分析

绘图窗体
turtle.setup(width,height,startx,starty)
  • width:窗口宽度如果值是整数,表示像素值;如果值是小数,表示窗口宽度与屏幕的比例。
  • height:窗口宽度,如果值是整数,表示像素值;如果值是小数,表示窗口高度与屏幕的比例。
  • startx:窗口左侧与屏幕左侧的像素距离,如果值是None,窗口位于屏幕水平中央。
  • starty:窗口顶部与屏幕顶部的像素距离,如果值是None,窗口位于屏幕垂直中央,如果没有值,保持默认,所以setup函数不是必要的。
角度坐标体系
turtle.seth(angle)
  • seth只改变海龟行进方向,但不前进
  • angle为绝对度数
  • 空间坐标体系分为绝对坐标(左180右0)和海龟坐标(前进方向和后退方向)。

angle表示海龟在当前行进的方向上旋转的角度。

turtle.left(angle)
turtle.right(angle)
画笔控制函数
turtle.penup()
turtle.pendown()

抬起画笔和落下画笔,之后移动画笔不绘制形状

turtle.pensize(width)

用来设置画笔尺寸

turtle.width()

设置画笔宽度,当无参数输入时返回当前画笔宽度。width是设置的画笔宽度,当为None或空,则函数返回当前画笔宽度。

turtle.pencolor("purple")


  • 又三种形式,可以直接输英文名称,可以输RGB的小数值,可以输RGB的元组值(双括号)
  • RGB色彩模式,默认采用小数值,可切换为整数值。1.0:RGN小数值模式。255:RGB整数值模式。
运动控制函数
turtle.fd(d)

走直线,d可以为负数

turtle.circle(r,extent=None)

根据半径r绘制extent角度的弧形

半径为正数时,半径在小海龟的左侧。半径为负数时,半径在右侧。

循环语句和range()函数
for<变量> in range(次数)
    <被循环执行的语句>

range函数:产生循环计数序列。

  • range(N):产生0到N-1的整数序列,共N个
  • range(M,N):产生M到N-1个整数序列,共N-M个

练习

  • 画图形的问题一定要注意读题,分清同心圆,六角形的区别。
import turtle
for i in range(9):
 turtle.circle(10 + 10*i)
 turtle.right(90)
 turtle.penup()
 turtle.fd(10)
 turtle.pendown()
 turtle.left(90)

#同心圆
  • 分段绘制蟒蛇的时候可以引用三个函数,在主函数力进行画笔的基本设置。

第三章 基本数据类型

数字类型

整数类型(可正可负,没有取值范围限制)
  • 四种进制表示:十进制,二进制,八进制和十六进制
  • 默认采用十进制,其他进制需要增加引导符号:
    • 二进制:0b或0B
    • 八进制:0o或0O
    • 十六进制:0x或0X
  • 内置函数pow测试整数类型的取值范围
浮点数类型
  • 必须带有小数部分
  • 两种表示方法:十进制表示或科学计数法(e a*10的b次方)
  • 浮点数取值范围和小数精度都存在限制,但常规计算可忽略。
  • 浮点数间运算存在不确定尾数。
  • 高精度浮点数运算类型:标准库decimal
a=decimal.Decimal('3.1415926') #高精度数字的表示需要使用单引号
decimal.getcontext().prec=20 #控制位数
复数类型
  • 复数类型的实数部分和虚数部分都是浮点数类型
  • 通过后缀J或j来修饰
().real  #获得实数部分
().imag  #获得虚数部分


练习

  • 为什么Python语言要同时提供整数类型和浮点数类型

    因为 Python 的整数取值不设限,只受配置影响;浮点数却有限制,最大浮点数是

    1.7976931348623157e+308。也就是说,如果没有整数数据类型,超过 1.7976931348623157e+308

    的整数将无法计算。

  • 进制表示

  • -77的科学计数法:-7.700000e+01

  • 复数2.3e+3-1.34e-3j的实部是2300.0 虚部是-0.00134

数字类型的操作

内置的数值运算操作符
操作符及其使用描述
x+yx和y的和
x-yx和y的差
x*yx和y的积
x/yx和y的商
x//yx和y的整数商,即不大于x和y之商的最大整数
x%yx与y之商的余数,也称为模运算
-xx的负值
+xx本身
x**yx的y次幂
  • 二元操作符
    • **x op=y ** ** x=x op y ** op和二元操作符之间没有空格。
  • 数字类型的关系
    • 类型见进行混合运算,生成结果为“最宽”类型
    • 整数→浮点数→复数
内置的数值运算函数
函数描述
abs(x)绝对值,x的绝对值
divmod(x,y)商余,输出两个值(x//y,x%y)
pow(x,y[,z])幂余(x**y)%z 【,z】表示参数z可省略
round(x,y)对x四舍五入,保留y位小数。round(x)返回四舍五入的整数值
max(x1,x2,xn)获得最大值,n没有限定
min(x1,x2,xn)获得最小值,n没有限定
  • 模运算:(%)
    • day%7表示日期
    • 判断n的奇偶:n%2等于0或1
    • 模运算n%m能够将整数映射到【0,m-1】的区间中。
内置的数字类型转换函数
函数描述
int(x)将x转换成整数,x可以为浮点数或字符串
float(x)返回浮点数x或者字符串x所对应的整数类型
complex(x)生成一个复数,实部为re(可以是整数,浮点数,字符串),虚部为im(可以为整数或浮点数但不能为字符串)
  • 操作符的优先级:先乘幂,后乘除。
  • 多个幂就是从右到左。

math库的使用

  • math库是Python提供的内置数学类函数库。,不支持复数类型,仅支持整数和浮点数类型。math一共提供了4个数学常数和44个函数。包括16个数值表示函数,8个幂对数函数,16个三角对数函数和4个高等特殊函数。

  • 引用:使用保留字import

  • 使用:引用后math.ceil(10,2)或from math import <函数名>或 from math import *所有函数采用<函数名>()形式使用

  • pow后面可以跟分数。

天天向上的力量

  • 为什么非要使用程序呢?
    • 因为如果使用变量的话,只要一处修改即可。
    • 因为如果使用变量的话,只要一处修改即可。
    • 循环思维:采用循环模拟365天过程,抽象+自动化
import math
dayfactor=0.01
dayup=math.pow((1.0+dayfactor),365)
daydown=math.pow((1.0-dayfactor),365)
print("向上:{:.2f},向下:{:.2f}.".format(dayup,daydown) 
  • 每周工作五天,休息两天,休息日水平下降0.01,工作日要努力到什么程度,一年后的水平才能和每天努力1%取得的效果一样呢?
def dayUp(df):
    dayup=1.0
    for i in range(365):
        if i % 7 in[6,0]:
            dayup=dayup*(1-0.01)
        else:
            dayup=dayup*(1+df)
    return dayup
dayfactor=0.01
while(dayUp(dayfactor)<37.78):
    dayfactor +=0.001
print("每天的努力参数是:{:.3f}.".format(dayfactor))




字符串类型及其操作

获得从起始位置pos开始长度为 3的子串:weekAbbr=weekstr[pos:pos+3]

— 缺点是:所剪切的字符串的长度必须相同。长度不同需要其他语句的辅助。

\a蜂鸣,响铃
\b回退,向后退一格
\f换页
\n换行,光标移动到下行首行
\r回车,光标移动到本行首行
\t水平制表
\v垂直制表
\0NULL,什么都不做
  • 字符串操作符

  • 字符串处理函数

len(x)返回字符串x的长度,也可返回其他组合数据类型元素个数
str(x)任意类型x所对应的字符串形式
chr(x)返回Unicode编码x对应的单字符
ord(x)返回单字符对应的Unicode编码
hex(x)返回整数x对应十六进制的小写字符串
oct(x)返回整数x对应的八进制数的小写字符串2
  • Unicode编码:
    • 统一字符串编码,即覆盖几乎所有字符的编码方式。
    • 从0到1114111空间,每个编码对应一个字符。
    • Python字符串中每个字符都是Unicode编码。
  • 凯撒密码(对字符串进行mod运算)
  • 字符串处理方法:
    • “方法”函数:方法特指.()风格中()
    • 方法本身也是函数,但与有关,.()风格使用的字符串及变量也是
    • 字符串处理函数
返回字符串的副本,全部字符小写\大写str.lower()或str.upper()
返回一个列表,由str根据sep被分隔的部分组成“A,B,C”.split(“,”),结果为[‘A’,‘B’,‘C’]str.split(sep=None)
返回子串sub在str中出现的次数,“a apple a day”.count(“a”)结果为4str.count(sub)
返回字符串的str副本,所有old子串被替换为new“str.replace(old,new)
字符串str根据宽度width居中,fiilchar可选str.center(width[,fillchar]
从str中去掉在其左侧和右侧chars中列出的字符str.strip(chars)
在iter变量除最后元素外每个元素后增加一个strstr.join(iter)
字符串类型的表示
  • 单引号字符串:单引号表示,可以使用双引号作为字符串的一部分。
  • 双引号字符串:双引号表示,可以使用单引号作为字符串的一部分。
  • 三引号字符串:用一对三单引号或三双引号表示,可表示多行字符。
  • input用来输入字符串,print用来输出字符串,name用来存储用户的名字。
  • 字符串的符号体系:正向递增序号和反向递减序号
  • 字符串提供区间访问方式。【N:M】如果缺项,则表示字符串把开始或结束索引值设为默认值。
  • 字符串以Unicode编码存储,因此,字符串的英文字符和中文字符都算作一个字符。
  • 反斜杠()是一个特殊字符,在字符串中表示转义,即该字符串与后面相邻的一个字符共同组成了新的含义。
    • 例题:获取星期字符串。
    • 表示:中括号,用list函数将元组或字符串转化为列表,直接使用list函数会返回一个空列表。
weekstr="星期一星期二星期三星期四星期五星期六星期日"
weekid=eval(input("请输入星期数字(1-7):"))
pos=(weekid-1)*3
print(weekstr[pos:pos+3])

字符串类型的格式化

  • Python支持的两种字符串格式化方法: 一种是类似C语言中printf格式化方法,另一种采用专门的str.format()格式化方法。
  • format()格式化方法的基本使用:

<模板字符串>.format(逗号分隔的参数)

,分隔的参数按照序号关系替换到模板字符串的槽中。槽用大括号表示,如果大括号中没有序号,则按照出现顺序替换。

  • 槽中,可以通过数字序号来指定内容。
  • 对format方法的格式控制。

<类型>: 表示输出整数和浮点数类型的格式规则。对于整数类型输出格式包括以下六种。

b:输出整数的二进制方式。

c:输出整数对应的Unicode字符

d:输出整数的十进制方式。

o:输出整数的八进制方式。

x:输出整数的小写16进制方式。

X:输出整数的大写16进制方式。

对于浮点数类型输出格式包括以下四种。

e:输出浮点数对应的小写字母e的指数形式。

E:输出浮点数对应的大写字母E的指数形式。

f:输出浮点数的标准浮点形式。

%:输出浮点数的百分形式。

  • 字符串和字节流:
    • 字节流是字节组成的序列字节由固定的八个比特组成。因此字节流从二进制角度有确定的长度和储存空间。
    • 字符串由编码字符的序列组成,字符根据编码不同,长度也不相同,因此从存储空间角度字符串和字节流不相同。
    • 硬盘上所有文件都以字节形式存储,例如文本图片及视频等。真正存储和传输数据时都是以字节为单位,字符值在内存中形成,由字节流经过编码处理后产生。
time库介绍
  • time库是Python中处理时间的标准库。提供获取系统时间并格式化输出功能
    。提供系统级精确计时功能,用于程序性能分析。
  • 时间获取
time()获取当前时间戳及计算机内部时间值,浮点数。
ctime()获取当前时间,并以异读方式表示返回字符串。‘Fri Jan 26 12:11:16 2018’
gmtime()获取当前时间,表示为计算机可处理的时间格式
  • 时间格式化
strftime(tpl,ts)tpl是格式化模板字符串用来定义输出效果。tsh是计算机内部时间类型变量。

8DKR2UTkUPTZXgvRi%2Fimage.png&pos_id=img-BZ3bikox-1710423366411)

  • 程序计时应用

    程序计时指测量起止动作所经历时间的过程。

perf_counter()返回一个CPU级别的精确时间计数值,单位为秒 由于这个计数值起点不确定,连续调用差值才有意义.
sleep(s)s拟休眠的时间,单位是秒,可以是浮点数
def wait():

  time.sleep(3.3)
  #程序等待3.3秒后再退出

文本进度条
  • 采用字符串方式打印可以动态变化的文本进度条。进度条需要能在一行中逐渐变化。
  • 获得文本进度条的变化时间:采用sleep()模拟一个持续的进度。
  • 多行动态刷新:
import time
scale=10
print("------执行开始------")
for i in range(scale+1):
    a='*'*i
    b='·'*(scale-i)
    c=(i/scale)*100
    print("{:^3.0f}%[{}->{}]".format(c,a,b))
    time.sleep(0.1)
print("------执行结束------")
  • 单行动态刷新

    刷新的关键是\r

    刷新的本质是:用后打印的字符覆盖之前的字符。

    不能换行:print()需要被控制。

    要能回退:打印后光标退回到之前的位置 \r

import time
for i in range(101):
    print("\r{:3}%".format(i),end="")
    time.sleep(0.05)
  • 带刷新的文本进度条
import time
scale=50
print("执行开始".center(scale//2,"-"))
start=time.perf_counter()
for i in range(scale+1):
    a='*'*i
    b='·'*(scale-i)
    c=(i/scale)*100
    dur=time.perf_counter()-start
    print("\r{:^3.0f}%[{}->{}]{:.2f}s".format(c,a,b,dur),end='')
    time.sleep(0.1)
print("\n"+"执行结束".center(scale//2,'-'))   
  • 拓展:

在任何运行时间需要较长的程序中增加进度条,在任何希望提高用户体验的应用中增加进度条,进度条是人机交互的纽带之一

  • 文本进度条的不同设计函数

练习

  • 进度条反映了软件的执行速度,给出三种提高软件执行速度的方法:设备方面:使用性能更强的处理器;或使用固态硬盘等设备提高计算机整体速度。软件自身:在编写时进行代码优化。编译时采用静态编译(Python 不存在编译的问题)。
  • str.center()使用的语法为 str.center(width[, fillchar]),其功能是返回一个指定的宽度width 居中的字符串,fillchar 为填充的字符,默认为空格。
  • 将转义符\r 放到字符串尾部是对程序没有影响;然而如果放到其他地方,会导致\r 前面的所有字符不显示,因为每次输出到\r,指针又退回了行首,如果后面的内容足够长,后面的内容会将其覆盖。
  • 天天向上续。尽管每天坚持,但人的能力发展并不是无限的,它符合特定模型。假设能力增长符合如下带有平台期的模型:以7天为周期,连续学习3天能力值不变,从第4天开始至第7天每天能力增长为前一天的1%。如果7天中有1天间断学习,则周期从头计算。请编写程序回答,如果初识能力值为1,连续学习365天后能力值是多少?
    3.3 天天向上续。采用程序练习题3.2的能力增长模型,如果初始能力值为1,固定每10天休息1天,365天后能力值是多少?如果每15天体息1天呢?
dayup=1
dayfactor=0.01
period=[4,5,6,0]
decrease=0
for j in range(1,366):
    temp=j-decrease
    tom=temp%7
    if j%10==0:
        decrease+=j-(tom-1)
        tom=1
    if tom in period:
        dayup=dayup*(1+dayfactor)   
print('%f the result is %.2f'%(dayfactor,dayup))
  • 回文数判断:反向排列所得的自然数与原数相等。
while 1:
    hui=input("请输入一个五位数或用e退出:")
    if len(hui)==5:
        if eval(hui)==eval(hui[-1:]+hui[3:4]+hui[2:3]+hui[1:2]+hui[0:1]):
            print("这是一个回文素数")
        else:
            print("这不是一个回文素数")
    elif hui[-1:] in ['e','E']:
        break
    else:
        print("您的输入有误")
        
  • 田字格的输出:控制第零行,第五行,第十行输出横线,其余输出竖线,所以用if-else判断即可。
for i in range(11):
    if i in [0,5,10]:
        print("+----+----+")
    else:
        print("|    |    |")
  • 有进度块的进度条
from tqdm import tqdm
from time import sleep
for i in tqdm(range(1,100)):
     print("")
     sleep(0.3)

第四章 程序的控制结构

程序的基本结构

  • 一个计算问题描述的方法:问题IPO描述(输入,处理,输出),流程图描述,Python代码描述。

程序的分支结构

  • 单分支结构:if语句

    • 根据判断条件结果而选择不同向前路径的运行方式
    • 要用到的比较:字符串本质上是对应Unicode编码的比较,比较顺序按字典进行。
  • 二分支结构:if-else语句

    • 根据判断条件结果而选择不同向前路径的运行方式

    • 紧凑形式:适用于简单表达式的二分支结构

  • 多分支结构:if-elif-else

    • 对不同分数分级的问题:注意多条件之间的包含关系,注意变量取值范围的覆盖**。**

    因为输入满足多分支第一个条件,执行后跳出了整个多分支。应该将成绩从高到低作为判断条件。

  • 条件判断:

程序的异常处理

  • 标注异常类型后,仅响应该异常 异常类型名字等同于变量

练习:

1、分别阐述try,except,else,finally保留字在异常处理中的作用:

try 语句块中放置想要检测的部分;except 语句块中放置想要捕获的异常,以及出

现异常后的处理;else 语句块中放置不出现异常时要执行的部分;finally 语句块中放置无论如

何都必须执行的部分,常用在使程序继续执行。

2、if-else语句也能够判断用户输入的合规性。

身体质量指数BMI

  • 定义:BMI=体重/身高的平方

补充:Python认为x≤y≤z是合法的。

height,weight=eval(input("请输入身高和体重,用逗号隔开"))
bmi=weight/pow(height,2)
print("BMI数值为:{:.2f}".format(bmi))
who,nat="",""
if bmi<18.5:
    who,nat="偏瘦","偏胖"
elif 18.5<=bmi<24:
    who,nat="正常","正常"
elif 24<=bmi<25:
    who,nat="正常","偏胖"
elif 25<=bmi<28:
    who,nat="偏胖","偏胖"
elif 28<=bmi<30:
    who,nat="偏胖","肥胖"
else:
    who,nat="肥胖","肥胖"
print("BMI 指标为:国际'{0}', 国内'{1}'".format(who, nat))
  • 多分支条件之间的覆盖是重要问题。程序可运行,但不正确,要注意多分支。分支结构是程序的重要框架,读程序先看分支

练习:

  • 条件由小到大写的时候,只写判断条件的后半部分:因为没必要,上一个条件的上限恰好是下一个条件的下限,各个区间是相连的。不存在冲突。
  • 24≤28<25:

这个语句的运算顺序是 24<=(28<25), 其中 28<25 的运算结果为 False,然后

计算 24<=False,相当于计算 24<=0,输出 False。

  • 引号中反斜杠的作用:语句换行,表示下一行与上一行是同一行语句。

程序的循环结构

for循环和while循环的区别

一、循环的结构不同

for循环的表达式为:for(单次表达式;条件表达式;末尾循环体){中间循环体;}。

while循环的表达式为:while(表达式){循环体}。
二、执行条件的判断方式不同

for循环执行末尾循环体后将再次进行条件判断,若条件还成立,则继续重复上述循环,当条件不成立时则跳出当下for循环。

while循环当满足条件时进入循环,进入循环后,当条件不满足时,执行完循环体内全部语句后再跳出(而不是立即跳出循环)。

三、使用的目的不同

for循环的目的是为了限制循环体的执行次数,使结果更精确。

while循环的目的是为了反复执行语句或代码块。

四、语法不同

for循环的语法为:for (变量 = 开始值;变量 <= 结束值;变量 = 变量 + 步进值) {需执行的代码 }。

while循环的语法为:while (<条件>) {需执行的代码 }。
————————————————
版权声明:本文为CSDN博主「火兰」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/qq_47443027/article/details/115308266

遍历循环for语句
  • 从遍历结构中逐一提取元素,放在循环变量中。由保留字for和in组成,完整遍历所有元素后结束每次循环,所获得元素放入循环变量,并执行一次语句块。

  • 遍历由range()函数产生的数字序列,产生循环。

  • s是字符串,遍历字符串每个字符,产生循环

  • 列表遍历循环:ls是一个列表,遍历其每个元素,产生循环

  • fi是一个文件标识符,遍历其每行,产生循环

无限循环:while语句
  • 反复执行语句块,直到条件不满足时结束
  • Ctrl+C可以退出执行。
循环控制保留字:
  • break和continue语句的区别:

1、break用于跳出一个循环体或者完全结束一个循环,不仅可以结束其所在的循环,还可结束其外层循环。

注意:
(1)只能在循环体内和switch语句体内使用break。
(2)不管是哪种循环,一旦在循环体中遇到break,系统将完全结束循环,开始执行循环之后的代码。
(3)当break出现在循环体中的switch语句体内时,起作用只是跳出该switch语句体,并不能终止循环体的执行。若想强行终止循环体的执行,可以在循环体中,但并不在switch语句中设置break语句,满足某种条件则跳出本层循环体。

2、continue语句的作用是跳过本次循环体中剩下尚未执行的语句,立即进行下一次的循环条件判定,可以理解为只是中止(跳过)本次循环,接着开始下一次循环。

注意:
(1)continue语句并没有使整个循环终止。
(2)continue 只能在循环语句中使用,即只能在 for、while 和 do…while 语句中使用。

  • 循环的高级用法:循环与else

当循环没有被break语句退出时,执行else语句块

else语句块作为"正常"完成循环的奖励

这里else的用法与异常处理中else用法相似

  • 所有for语句都可以用while循环语句改写。

random库的使用

  • 伪随机数: 采用梅森旋转算法生成的(伪)随机序列中元素
  • random库主要用于生成随机数
  • 使用random库: import random
  • 随机数函数
seed(a=None)初始化给定的随机数种子,默认为当前系统时间
random()生成一个[0.0, 1.0)之间的随机小数
生成一个【a,b】之间的整数
生成一个[m, n)之间以k为步长的随机整数
getrandbits(k)生成一个k比特长的随机整数
uniform(a,b)生成一个[a, b]之间的随机小数
choice(seq)从序列seq中随机选择一个元素
stuffle(seq)将序列seq中元素随机排列,返回打乱后的序列
sample(pop,k)宠pop类型中随机选取k个元素,以列表类型返回
  • 使用的时候前面一定要带上random。比如哦:random.randint(0,100)
import random
s='abcdefghij'
for i in range(4):
    print(s[random.randint(0,len(s)-1)])
  • 如果记不住的话,可以把字符串转化为列表,然后用randint。

圆周率的计算

  • 公式法:
pi=0
N=100
for k in range(N):
    pi+=1/pow(16,k)*(\
        4/(8*k+1)-2/(8*k+4)-\
        1/(8*k+5)-1/(8*k+6))
print(pi)

  • 蒙特卡罗方法:随机向单位正方形和圆结构,抛洒大量的“飞镖点”,计算每个点到圆心的距离,从而判断该点在圆内还是圆外,用圆内的点数除以点总数就是π/4值。随机点数量越大,越充分覆盖整个图形,计算得到的π值就越精确。—离散点值表示图形的面积。

    IPO:

    输入:抛点数

    处理:计算每个点到圆心的距离,统计在圆内点的数量。

    输出:圆周率

#----计算pi的值----
from random import random
from math import sqrt
from time import perf_counter
DARTS=100000      #抛点数
hits=0.0
perf_counter()
for i in range(1,DARTS+1):
    x,y=random(),random()
    dist=sqrt(x**2+y**2)
    if dist<=1.0:
        hits=hits+1
pi=4*(hits/DARTS)
print("pi值是{}".format(pi))
print("运行时间是:{:.5f}s".format(perf_counter()))


- 数学思维:找到公式,利用公式求解

计算思维:抽象一种过程,用计算机自动化求解
- 使用time库的计时方法获得程序运行时间

改变撒点数量,理解程序运行时间的分布

初步掌握简单的程序性能分析方法

练习:

[4.19]: DARTS = 10000000 时,准确率比较高,结果是 3.1420104。

[4.20]: 将第 11 句改为 dist <= 2.0,这样无论 xy 怎样变化,它们的平方和始终小于 2,结

果也是一样的,虽然是错的。

[4.21]: (1) 蒙特卡罗搜索树。下过围棋的同学都知道棋手的水平取决于他能够推演的步数,

专业棋手一般能推演十几步以上,然而这个看似简单的东西对早期计算机来说是个噩梦。因此

在机器围棋领域,出现了一种算法叫蒙特卡罗搜索树,它就是运用了蒙特卡罗方法来缩小计算

机的搜索范围。从而使计算机拥有与人类棋手匹敌的推演步数。

(2) 蒙特卡罗积分等。

程序练习题:

  • 猜数游戏
from random import *
seed(100)
num=randint(0,100)
tim=0
while 1:
    try:
        putnum=eval(input("请输入您猜测的数字:"))
        tim+=1
        if putnum>num:
            print("遗憾!太大了")
        elif putnum<num:
            print("遗憾!太小了")
        elif putnum==num:
            print("预测{}次,你猜中了".format(tim))
            break
        else:
            print("输入内容必须为整数!")
    except:
        print("输入有误!")
  • 统计不同字符的个数:
stri=input("请输入你想要的字符串:")
kong=0
alpha=0
chi=0
num=0
other=0
for i in stri:
    if i==" ":
        kong+=1
    elif '0'<=i<='9':
        num+=1
    elif i>u'\u4e00' and i<=u'\u9fa5':
        chi+=1
    elif True==i.isalpha():  #统计字母的个数
        alpha+=1
    else:
        other+=1
print("你输入的字符串中有{}个空格,{}个数字,{}个中文,{}个英文字符,{}个其他字符".format(kong,num,chi,alpha,other))

      
  • 最大公约数计算
a,b=eval(input("请输入两个整数,中间用逗号隔开:"))
c=a*b
if a<b:
    a,b=b,a
while False==(a in[0,1]):#a既不是0也不是1的时候进入循环
    b,a=a,b%a
c=c/b
print("最小公约数为:{},最大公倍数为{}".format(b,c))
  • 羊车门问题
import random
times = eval(input("请输入你希望模拟的次数:"))
pick_first_n = 0
pick_change_n = 0
for i in range(times):
 car = random.randint(0, 2) #生成哪个门后藏车
 pick_first = random.randint(0, 2) #初始随机选一个
 if pick_first == car: #如果直接选中,则初始选择正确,
pick_first_n 加 1,换选择一定不中
 pick_first_n += 1
 else: #如果初始选择没中,则主持人打开另一扇没车的门
后,换选择一定中
 pick_change_n += 1 #故 pick_change_n 加 1
pick_first_percent = pick_first_n / times #计算坚持不换选择的
胜率
pick_change_percent = pick_change_n / times #计算换选择的胜率
print("如果坚持初选,胜率为{:.2f}%".format(pick_first_percent * 
100))
print("如果改变初选,胜率为{:.2f}%".format(pick_change_percent * 
100))
  • 用异常处理改写温度实例:
TempStr = input('请输入带有符号的温度值:')
if TempStr[-1] in ['F','f']:
try:
C = (eval(TempStr[:-1]) - 32)/1.8
print('转换后的温度是{:.2f}C'.format(C))
except:
print('您输入的温度格式有误!')
elif TempStr[-1] in ['C','c']:
try:
F = 1.8 * (eval(TempStr[:-1])) + 32 
print('转换后的温度是{:.2f}F'.format(F))
except:
print('您输入的温度格式有误!')
else:
print('您输入的温度格式有误!')

第五章 函数和代码复用

函数的基本使用

函数的定义
  • 函数是一段具有特定功能的、可重复使用的语句组。函数是一种功能的抽象,一般函数表达特定功能两个作用:降低编程难度 和 代码复用。

  • 函数定义时,所指定的参数是一种占位符

函数定义后,如果不经过调用,不会被执行

函数定义时,参数是输入、函数体是处理、结果是输出 (IPO)

函数的调用
  • 调用是运行函数代码的方式
  • 调用时要给出实际参数,

实际参数替换定义中的参数

函数调用后得到返回值

  • 调用程序在调用处暂停执行。
    • 在调用时将实参复制给函数的形参
    • 执行函数体语句
    • 函数调用结束给出返回值,程序回到调用前的暂停处继续执行。
  • 引入思想:函数式编程—把程序过程尽量写成一系列函数调用,通过函数进一步提高封装级别。
lambda函数

定义:lambda函数是一种匿名函数,即没有名字的函数

使用lambda保留字定义,函数名是返回结果

lambda函数用于定义简单的、能够在一行内表示的函数。

语法格式如下:

<函数名>=lambda<参数列表>:<表达式>

用来定义简单的,可以在一行内表示的函数。

习题:

def f1():
f2()
def f2():
print("函数f2()")
f1()

合法,因为 Python 语言是解释执行,即只要在真正调用函数之前定义函数,都可以

进行合法调用。

函数的参数传递

  • 参数个数:函数可以有参数,也可以没有,但必须保留括号。

  • 可选参数传递:函数定义时可以为某些参数指定默认值,构成可选参数

  • 可变参数传递:函数定义时可以设计可变数量参数,既不确定参数总数量。带星号的可变参数只能出现在参数列表的最后,这些参数被当做元祖类型传递到函数中。

  • 参数传递的两种方式:函数调用时,参数可以按照位置或名称方式(这个可以不按照顺序)传递。

  • 函数的返回值:return保留字用来传递返回值

函数可以有返回值,也可以没有,可以有return,也可以没有

return可以传递0个返回值,也可以传递任意多个返回值

  • 局部变量和全局变量:

    • 局部变量和全局变量是不同变量。

    • 局部变量是函数内部的占位符,与全局变量可能重名但不同

    • 函数运算结束后,局部变量被释放

    • 可以使用global保留字在函数内部使用全局变量

    • 局部变量为组合数据类型且未创建,等同于全局变量
      。—意思是列表类型未被修改。

    • 如果在函数内部被定义了,那么ls真实创建,ls为局部变量。

    • 基本数据类型,无论是否重名,局部变量与全局变量不同

    • 组合数据类型,如果局部变量未真实创建,则是全局变量

练习:

1、如何定义有可选参数的函数?

在函数定义时,直接为可选参数指定默认值。可选参数必须定义在非可选参数后面,

可选参数可以有多个。

2、如何定义带有可变数量参数的函数?

在函数定义时,可变参数通过在参数前增加星号(*)实现。可变数量参数只能在参数列表最后,即它只能有一个。

3、return返回的数据是什么类型:元组类型。

4、参数的位置传递和名称传递有什么优缺点?

位置传递:支持可变数量参数,但容易忘记实参的含义;

名称传递:不易忘记实参的含义,但不支持可变数量参数。

5、在函数中操作全局列表类型变量时需要注意什么问题?如果函数里没有创建同名变量,则可以直接使用,不需 global 声明。

datetime库的使用

datetime库概述
  • datetime函数:

    • datetime.date :日期表示类,可以表示年,月,日。
    • datetime.time:时间表示类,可以表示小时,分钟,秒,毫秒等。
    • datetime.datetime:日期和时间表示的类,功能覆盖date和time类。
    • datetime.timedelta:与时区有关的信息表示类。
  • datetime库解析:

    • datetime类的使用方法是先创建一个datetime对象,然后通过对象的方法和属性显示时间。
    • datetime.now()获得当前日期和时间对象。
    • datetime.utcnow()表示当前日期和时间的UTC表示,精确到微妙。
    • datetime类的常用属性:

    外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

    • 时间的格式化方法:

    • strftime()方法的格式化控制字符:

    练习:

    1、举一个例子,输出美式日期格式:

    print(“{0:%I}:{0:%M} {0:%b} {0:%d} {0:%Y}”.format(datetime.now()))

    2、datetime 对象可以直接做加减运算,所以可以用这样的方式给程序计时:

    Start = datetime.now()

    End = datetime.now()

    Cost = End – Start

    Print(Cost)

七段数码管绘制

  • 基本思路:步骤1:绘制单个数字对应的数码管

步骤2:获得一串数字,绘制对应的数码管

步骤3:获得当前系统时间,绘制对应的数码管
- 步骤一:绘制单个数码管

![](https://secure2.wostatic.cn/static/2incr4mhRcWt8eiBF8SKf1/image.png)
import turtle
def drawLine(draw):#绘制单段数码管
    turtle.pendown() if draw else turtle.penup()
    turtle.fd(40)
    turtle.right(90)
def drawDigit(digit):#根据数字绘制七段数码管
    drawLine(True) if digit in [2,3,4,5,6,8,9] else drawLine(False)
    drawLine(True) if digit in [0,1,3,4,5,6,7,8,9] else drawLine(False)
    drawLine(True) if digit in [0,2,3,5,6,8,9] else drawLine(False)
    drawLine(True) if digit in [0,2,6,8] else drawLine(False)
    turtle.left(90)
    drawLine(True) if digit in [0,4,5,6,8,9] else drawLine(False)
    drawLine(True) if digit in [0,2,3,5,6,7,8,9] else drawLine(False)
    drawLine(True) if digit in [0,1,2,3,4,7,8,9] else drawLine(False)
    turtle.left(180)
    turtle.penup()#为后续数字确定位置
    turtle.fd(20)#为绘制后续数字确定位置
def drawDate(date):
    for i in date:
        drawDigit(eval(i))
def main():
    turtle.setup(800,350,200,200)
    turtle.penup()
    turtle.fd(-300)
    turtle.pensize(5)
    drawDate('20181010')
    turtle.hideturtle()
    turtle.done()
main()

  • 增加七段数码管之间线条间隔
import turtle
def drawGap():
    turtle.penup()
    turtle.fd(5)
def drawLine(draw):
    drawGap()#绘制单段数码管
    turtle.pendown() if draw else turtle.penup()
    turtle.fd(40)
    drawGap()
    turtle.right(90)
def drawDigit(digit):#根据数字绘制七段数码管
    drawLine(True) if digit in [2,3,4,5,6,8,9] else drawLine(False)
    drawLine(True) if digit in [0,1,3,4,5,6,7,8,9] else drawLine(False)
    drawLine(True) if digit in [0,2,3,5,6,8,9] else drawLine(False)
    drawLine(True) if digit in [0,2,6,8] else drawLine(False)
    turtle.left(90)
    drawLine(True) if digit in [0,4,5,6,8,9] else drawLine(False)
    drawLine(True) if digit in [0,2,3,5,6,7,8,9] else drawLine(False)
    drawLine(True) if digit in [0,1,2,3,4,7,8,9] else drawLine(False)
    turtle.left(180)
    turtle.penup()#为后续数字确定位置
    turtle.fd(20)#为绘制后续数字确定位置
def drawDate(date):
    for i in date:
        drawDigit(eval(i))
def main():
    turtle.setup(800,350,200,200)
    turtle.penup()
    turtle.fd(-300)
    turtle.pensize(5)
    drawDate('20181010')
    turtle.hideturtle()
    turtle.done()
main()
  • 获取系统时间,绘制七段数码管
    • 使用time库获得系统当前时间,增加年月日标记,年月日颜色不同。
import turtle,time
def drawGap():
    turtle.penup()
    turtle.fd(5)
def drawLine(draw):
    drawGap()#绘制单段数码管
    turtle.pendown() if draw else turtle.penup()
    turtle.fd(40)
    drawGap()
    turtle.right(90)
def drawDigit(digit):#根据数字绘制七段数码管
    drawLine(True) if digit in [2,3,4,5,6,8,9] else drawLine(False)
    drawLine(True) if digit in [0,1,3,4,5,6,7,8,9] else drawLine(False)
    drawLine(True) if digit in [0,2,3,5,6,8,9] else drawLine(False)
    drawLine(True) if digit in [0,2,6,8] else drawLine(False)
    turtle.left(90)
    drawLine(True) if digit in [0,4,5,6,8,9] else drawLine(False)
    drawLine(True) if digit in [0,2,3,5,6,7,8,9] else drawLine(False)
    drawLine(True) if digit in [0,1,2,3,4,7,8,9] else drawLine(False)
    turtle.left(180)
    turtle.penup()#为后续数字确定位置
    turtle.fd(20)#为绘制后续数字确定位置
def drawDate(date):
    turtle.pencolor("red")
    for i in date:
        if i=='-':
            turtle.write('年',font=("Arial",18,"normal"))#相当于隐藏画笔的turtle形状
            turtle.pencolor("green")
            turtle.fd(40)
        elif i=='=':
            turtle.write('月',font=("Arial",18,"normal"))
            turtle.pencolor("blue")
            turtle.fd(40)
        elif i=='+':
            turtle.write('日',font=("Arial",18,"normal"))
        else:
            drawDigit(eval(i))
            
def main():
    turtle.setup(800,350,200,200)
    turtle.penup()
    turtle.fd(-300)
    turtle.pensize(5)
    drawDate(time.strftime('%Y-%m=%d+',time.gmtime()))
    turtle.hideturtle()
    turtle.done()
main()
- 模块化思维:确定模块接口,封装功能

规则化思维:抽象过程为规则,计算机自动执行

化繁为简:将大功能变为小功能组合,分而治之
-

(1) DrawLine 与 DrawDigit 属于紧耦合的关系, DrawLine 一旦改变,DrawDigit 内部就要做大幅度更改。

(2) DrawData 与turtle 中的 penup,pendown 方法则属于松耦合的关系,无论起笔落笔的方式如何变化,DrawData一定是在落笔之后的操作,它与起笔落笔没有关系。

代码复用与模块化设计

  • 代码复用
    • 把代码当成资源进行抽象
    • 代码资源化:程序代码是一种用来表达计算的"资源"

代码抽象化:使用函数等方法对代码赋予更高级别的定义

代码复用:同一份代码在需要时可以被重复使用
- 函数 和 对象 是代码复用的两种主要形式

![](https://secure2.wostatic.cn/static/j4ogXQhdN2cusrt8BwrMPV/image.png)
通过函数或对象封装将程序划分为模块及模块间的表达

具体包括:主程序、子程序和子程序间关系

分而治之:一种分而治之、分层抽象、体系化的设计思想

松耦合和紧耦合:

- 紧耦合:两个部分之间交流很多,无法独立存在
- 松耦合:两个部分之间交流较少,可以独立存在
- 模块内部紧耦合、模块之间松耦合
- ”使用函数“是“模块化设计“的必要条件。
- 过量使用函数会造成运行时频繁出入栈,浪费系统资源。

函数的递归

  • 定义:函数定义中调用函数自身的方式
  • 内存空间的一次次分配,直到遇到基例。
  • 两个关键特征:链条:计算过程存在递归链条

。基例:存在一个或多个不需要再次递归的基例

  • 类似数学归纳法:
递归的调用

递归本身是一个函数,需要函数定义方式描述

函数内部,采用分支语句对输入参数进行判断

基例和链条,分别编写对应代码

  • 阶乘:
def fact(n):
    if n==0:
        return 1
    else:
        return n*fact(n-1)
num=eval(input())
print(fact(abs(int(num))))

  • 字符串反转:
def rvs(s):
    if s=="":
        return s
    else:
        return rvs(s[1:])+s[0]
str=input("请输入一个字符串")
print(rvs(str))
  • 汉诺塔
count=0
def hanoi(n,src,dst,mid):
    global count
    if n==1:
        print("{}:{}-->{}".format(1,src,dst))
        count+=1
    else:
        hanoi(n-1,src,mid,dst)
        print("{}:{}-->{}".format(n,src,dst))
        count+=1
        hanoi(n-1,mid,dst,src)
hanoi(3,"A","C","B")
print(count)

练习:

1、构建递归的基例:数学归纳法,递推式等。

2、递归和循环有什么区别:

循环由已知推未知,不断向后;递归由未知寻找已知,不断向前,递归的实质是出入栈,效率较低。

pyinstaller库的使用

  • 将.py源代码转换成无需源代码的可执行文件

  • 使用

  • 常用参数:

科赫曲线绘制

import turtle
def koch(size,n):
    if n==0:
        turtle.fd(size)
    else:
        for angle in [0,60,-120,60]:
            turtle.left(angle)
            koch(size/3,n-1)
def main():
    turtle.setup(600,600)
    turtle.speed(0)
    turtle.penup()
    turtle.goto(-200,100)
    turtle.pendown()
    turtle.pensize(2)
    level=5
    koch(400,level)
    turtle.right(120)
    koch(400,level)
    turtle.right(120)
    koch(400,level)
    turtle.hideturtle()
main()

修改分形几何绘制阶数

修改科赫曲线的基本定义及旋转角度

修改绘制科赫雪花的基础框架图形

练习:

  • 改变绘制过程的速度:改变 turtle.speed()中的参数值。
  • 反向绘制,从直线开始,中间部分向下绘制:修改 koch()函数,其他部分不变。
  • 修改颜色: 在设置画笔时加一行 turtle.pencolor(颜色名称)。

Python内置函数

  • type()函数对整数,浮点数,字符串进行类型判断。 整数 type(123), 浮点数 type(1E10),字符串 type(‘str’)。
  • 字符串可以使用 len()得到长度,而整数和浮点数不能得到长度,因为它们都是动态的,没有长度。

练习:

  • 绘制更大的田字格:
def drawsq(n):
    line=3*n+1
    for i in range(1,line+1):
        if i%3==1:
            print(n*"+----",end="")
            print("+")
        else:
            print("|    "*n,end="")
            print("|")
def main():
    n=eval(input("请输入您要的阶数:"))
    drawsq(n)
main()
  • 对自己生日的输出不少于10种日期格式:

  • 实现isPrime()函数,参数为整数,要有异常处理。如果整数是质数,返回True,否则返回False。

#质数是大于一的正整数,只能被1和它本身整除
def isprime():
    while True:
        num=eval(input("请输入大于1的整数"))
        if type(num)==int:
            break
        print("请输入一个大于一的整数:")
    if num<=1:
        return False
    elif 1<num<=3:
        return True
    elif num>3:
        for i in range(2,num):
            if num%i==0:
                return False
        return True
try:
    print(isprime())
except:
    print("请输入大于一的整数")

第六章 组合数据类型

定义

序列类型是一维元素向量,元素之间存在先后关系,通过序号访问。

  • 类型:字符串,元组,列表
  • 访问序列中的某个值只需要通过下标标出即可。
  • 元素之间有顺序关系,所以序列中可以存在数值相同而位置不同的元素。
  • 类型:字符串,元组,列表
    • 字符串:单一数据的有序组合
    • 元组:包含0个或多个数据项的不可变数据类型
    • 列表:可以修改数据项的数据类型。
  • 序列使用相同的索引体系:正向递增序号和反向递减序号。
x in s如果x是s的元素,则返回True
s+t连接两个列表
s*n将序列s复制n次
s[i:j:k]步骤分片,返回从i到j个元素以k为步长的子序列
min(s)求序列中的最小元素
len(s)求序列中的元素个数(长度)
max(s)求序列中的最大元素(通过ASCII码值进行比较)
s.index(x,i,j)从i到j位置第一次出现元素x的位置
s.count(x)序列s中元素x的个数
集合类型
  • 包含0或多个数据项的无序组合。
  • 集合中的元素不可重复,只能是固定的数据类型,例如整数,浮点数,字符串,元组等。还有能够进行哈希运算的类型。
  • 集合没有索引和位置的概念,不能分片,集合中的元素可以进行动态增加或删除。
  • 用大括号来赋值。
  • 集合类型能过滤掉重复元素。
w=set(("apple","cat","dog","human"))  #使用了两层括
S-T S.difference(T)返回一个新集合。包含在集合S但不在集合T中的元素
S-=T S.difference_update(T)更新集合S,包含在集合S但不在集合T中的元素
S&T S.intersection(T)返回一个新集合,同时包含集合S和T中的元素
S&=T S.intersection_update(T)更新集合S,同时包含集合S和T中的元素
S^T S.symmetric_difference(T)返回一个新集合,包含S和T中的元素,但不包含同时在S和T中的元素
S^=T S.symmetric_difference_update(T)更新集合S,包含S和T中的元素,但不包含同时在S和T中的元素
ST S.union(T)
S=T S.union_update(T)
S≤T S.issubset(T)如果S与T相同,或者S是T的子集返回True,用于判断真子集时去掉等号
  • 集合类型操作函数
s.add(x)如果x不在s中,插入
s.clear()移除s中的所有数据项
s.copy()返回集合的一个副本
s.discard()如果x在S中,移除,如果不在也不报错
s.pop()随机返回一个元素,如果s为空,产生keyerror异常(随机输出后还会删除,更新S
s.remove()如果x在S中,移除,如果不在产生异常
s.isdisjoint(T)如果两个集合没有相同的元素,返回True
映射类型
  • (键—值)数据项的组合,元素之间是 无序的。
  • 键值对是一种二元关系,源于属性和值的映射关系
  • 键表示的事一种属性,也可以理解为一个类别或项目。值是属性的内容。键值对刻画了一个属性和它的值。
  • 键值对讲映射关系结构化,用于储存和表达,映射类型主要以字典来实现。

练习

1、比较元组和集合的关系,思考怎么实现元组和集合的相互转换?

元组的表现形式是引号和小括号,集合的表现形式是引号和大括号;元组是元素不可更改的特殊列表,集合是无重复元素的无序组合。

2、序列,集合,映射在数据关系层面的含义:

序列是数值和位置的关系,集合是不重复的无序组合,映射是数值与名称的关系。

列表类型和操作

序列类型定义

序列是具有先后关系的一组元素

序列是一维元素向量,元素类型可以不同

类似数学元素序列: s0, s1, … , sn-1
元素间由序号引导,通过下标访问序列的特定元素

  • 序列类型通用操作符:

  • 序列类型通用函数和方法:

元组类型及操作

元组是一种序列类型,一旦创建就不能被修改

使用小括号 () 或 tuple() 创建,元素间用逗号 , 分隔

可以使用或不使用小括号

元组继承了序列类型的全部通用操作

元组因为创建后不能修改,因此没有特殊操作

使用或不使用小括号

列表类型的概念
  • 列表是包含0个或多个对象引用的有序序列,属于序列类型。
  • 灵活性:长度和内容都是可变的,可对列表中的数据进行增加,删除或替换。列表没有长度限制,元素类型可不同。
  • 支持成员关系操作符(in),长度计算函数(len),分片(【】),同时使用正向递增序号和反向递减序号,比较操作符(<,≤,==,≠,≥,>)—本质:单个数据项的逐个比较。

)

  • 列表类型操作函数和方法:

ls.index():返回元素索引。

  • 重要功能默写:

  • 元组用于元素不改变的应用场景,更多用于固定搭配场景

列表更加灵活,它是最常用的序列类型

最主要作用:表示一组有序数据,进而操作它们

序列类型的应用:
  • 元素遍历:

  • 数据保护: 如果不希望数据被程序所改变,转换成元组类型。

练习:

升序 sorted(ls),降序 sorted(ls, reverse = True)。

基本统计值计算

  • 需求:给出一组数,对它们有个概要理解
def getNum():#获得用户不定长度的输入
    nums=[]
    iNumStr=input("请输入数字(回车退出):")
    while iNumStr !="":
        nums.append(eval(iNumStr))
        iNumStr=input("请输入数字(回车退出):")
    return nums
def mean(numbers):#计算平均值
    s=0.0
    for num in numbers:
        s=s+num
    return s/len(numbers)
def dev(numbers,mean):#计算方差
    sdev=0.0
    for num in numbers:
        sdev=sdev+(num-mean)**2
    return pow(sdev/(len(numbers)-1),0.5)
def median(numbers):#计算中位数
    sorted(numbers)
    size=len(numbers)
    if size %2==0:
        med=(numbers[size//2-1]+numbers[size//2])/2
    else:
        med=numbers[size//2]
    return med
n=getNum()
m=mean(n)
print("平均值:{},方差:{:.2},中位数:{}".format(m,dev(n,m),median(n)))

获取多个数据:从控制台获取多个不确定数据的方法

分隔多个函数:模块化设计方法

充分利用函数:充分利用Python提供的内容函数

字典类型和操作

  • 字典类型定义:字典类型是“映射”的体现。键值对:键是数据索引的扩展

字典是键值对的集合,键值对之间无序

采用大括号{}和dict()创建,键值对用冒号: 表示

  • 在字典变量中,通过键获得值

  • 字典类型操作函数和方法:

    外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

    • 字典类型的重要功能:
  • 字典类型的应用场景:

    • 映射无处不在,键值对无处不在

例如:统计数据出现的次数,数据是键,次数是值

最主要作用:表达键值对数据,进而操作它们
- 元素遍历:

![](https://secure2.wostatic.cn/static/vn1R6miPRt3JBkAvgQBqjA/image.png)

- 注意:因为列表是可变的,不能作为键使用。字典里一个键只对应 1 个值。

jieba库的使用

  • 定义:jieba是优秀的中文分词第三方库
  • 中文文本需要通过分词获得单个的词语。

jieba是优秀的中文分词第三方库,需要额外安装

jieba库提供三种分词模式,最简单只需掌握一个函数

  • jieba分词的原理:利用一个中文词库,确定汉字之间的关联。概率

汉字间概率大的组成词组,形成分词结果

除了分词,用户还可以添加自定义的词组

  • jieba分词的三种模式:
    • 精确模式:把文本精确的切分开,不存在冗余单词
    • 全模式:把文本中所有可能的词语都扫描出来,有冗余
    • 搜索引擎模式:在精确模式基础上,对长词再次切分
  • jieba库常用函数:

文本词频统计

  • 实例:Python之禅

    • 写出5条写出优美代码的编程原则:

    (1) 清晰明了,规范统一;

    (2) 逻辑简洁,避免复杂逻辑;

    (3) 接口关系要清晰;

    (4) 函数功能扁平,避免太多层次嵌套;

    (5) 间隔要适当,每行代码解决适度问题。

d[chr(i+c)]=chr((i+13)%26 +c)

练习:

  • 随机密码生成:
from random import randint
def rancre():
    mi=''
    for i in range(8):
        u=randint(0,62)
        if u>=10:
            if 90<(u+55)<97:
                mi+=chr(u+62)
            else:
                mi+=chr(u+55)
            print("{}".format(u+55),end="")
        else:
            mi+='%d'%u
    return mi
def main():
    for i in range(1,11):
        print("生成的第{}个密码是:{}".format(i,rancre()))
main()

  • 重复元素判定:
def main():
    num=[]
    n=input("请输入一组数字(或者直接按回车结束程序):")
    while n!="":
        num.append(eval(n))
        n=input("请输入一组数字(或者按回车结束程序):")
    else:
        print("正在处理,请稍等")
        judge(num)
def judge(n):
    if len(n)==len(set(n)):
        print("鉴定完毕,没有重复的元素")
    else:
        print("有重复的元素,总共有{}个".format(len(n)-len(set(n))))
main()
  • 英文字符的统计
txt=input("请输入您想输入的英文句子:")
counts={}
ex=[',','.','?','!',':','"',';']
for i in txt:
    if i==" " or i in ex:
        continue
    else:
        if ord(i)<97:
            i=chr(ord(i)+32)
        counts[i]=counts.get(i,0)+1
items=list(counts.items())
items.sort(key=lambda x:x[1],reverse=True)
for u in range(len(items)):
    alpha,count=items[u]
    print("{}->{}".format(alpha,count))

第七章 文件和数据的格式化

文件的使用

  • 格式化:字符串格式化“{}{}{}”.format()将字符串按照一定的规格和式样进行规范。
  • 数据格式化:将一组数据按照一定的规格和式样进行规范:表示,存储,运算等。
文件的概述
  • 文件是一个存储在辅助存储器上的数据序列,可以包含任何数据内容。
  • 文件时数据的集合和抽象。
  • 文件展示形态:文本文件和二进制文件。
    • 文本文件:一般由特定编码的数字组成,如UTF-8编码,所以被看成是存储着的长字符串。由文本编辑器或文字处理软件创建,修改和阅读。例如:.txt .py
    • 二进制文件:直接由比特0和1组成,没有同意的字符编码。二进制文件只能看做字节流,不能看做字符串。例.png .avi文件
文件的打开关闭
  • 文件处理的步骤:打开—操作—关闭。
  • a=open( , )为文件的存储状态。 a.close() 为文件的占用状态。—这种方法可以避免同时操作。
  • open()函数的格式:
    • 变量名=open(文件名,打开模式)
    • 文件名:文件的实际名字,也可以是包含完整路径的名字,源文件同目录可省路径。
    • 打开模式有以下几种:(决定是文本还是二进制,读还是写)
‘r’只读模式,如果文件不存在,则返回异常FileNotFoundError,默认值
‘w’覆盖写,文件不存在则创建,文件存在则完全覆盖
‘x’创建写,文件不存在则创建,存在则返回异常FileExistsError
‘a’追加写模式,文件不存在则创建,存在则在文件最后追加内容
‘b’二进制文件模式
‘t’文本文件模式,默认值
‘+’与r/w/x/a一同使用,在原功能基础上增加同时读写功能
  • 文件的关闭:

  • 文件内容的读取:

  • 文件的全文本操作:

    • 一次读入,统一处理

    • 按数量读入,逐步处理

  • 文件的逐行操作:

    • 一次读入,分行处理:

    • 分行读入,逐行处理:

  • 数据的文件写入:

练习:

  • 若文件不存在,采用读取方式时,会发生什么情况?采用写入方式呢?

采用读方式,会报出 FileNotFoundError 异常;采用写方式,会创建此文件。

  • 如何从文件中读取30个字符?

file.read(30)

  • 采用open()函数打开Windows系统目录中的一个文件,会出现什么情况?

提示文件不存在,或者无权限操作。

自动轨迹绘制

步骤1:定义数据文件格式(接口)

步骤2:编写程序,根据文件接口解析参数绘制图形

步骤3:编制数据文件

  • 数据接口定义:
import turtle as t
t.title('自动轨迹绘制')
t.setup(800,600,0,0)
t.pencolor("red")
t.pensize(5)
#数据读取
datals=[]
f=open("E:\\Python-3.11.3\\自动轨迹绘制.txt")
for line in f:
    line=line.replace("\n","")
    datals.append(list(map(eval,line.split(","))))
f.close()
#自动绘制
for i in range(len(datals)):
    t.pencolor(datals[i][3],datals[i][4],datals[i][5])
    t.fd(datals[i][0])
    if datals[i][1]:
        t.right(datals[i][2])
    else:
        t.left(datals[i][2])
        

  • 理解方法思维:
    • 自动化思维:数据和功能分离,数据驱动的自动运行

接口化设计:格式化设计接口,清晰明了

二维数据应用:应用维度组织数据,二维数据最常用

  • 应用问题的扩展:
    • 扩展接口设计,增加更多控制接口

扩展功能设计,增加弧形等更多功能

扩展应用需求,发展自动轨迹绘制到动画绘制

一维数据的格式化和处理

数据的维度

从一个数据到一组数据:一个数据表达一个含义,一组数据表达一个或多个含义。

  • 定义:一组数据的组织形式
  • 一维数据:由对等关系的有序或无序数据构成,采用线性方式组织。
  • 对应列表、数组和集合等概念
  • 二维数据:由多个一维数据构成,是一维数据的组合形式。
    • 表格是典型的二维数据

其中,表头是二维数据的一部分

  • 高维数据:仅利用最基本的二元关系展示数据间的复杂结构。采用对象方式组织,属于整合度更好的数据组织方式。(如:键值对)
  • 数据的操作周期:存储—表示—操作

一维数据的表示
  • 如果数据间有序:使用列表类型
    • 列表类型可以表达一维有序数据

for循环可以遍历数据,进而对每个数据进行处理

  • 如果数据间无序:使用集合类型
    • 集合类型可以表达一维无序数据

for循环可以遍历数据,进而对每个数据进行处理

一维数据的处理
  • 方式一:空格分隔
    • 使用一个或多个空格分隔进行存储,不换行

缺点:数据中不能存在空格

  • 方式二:逗号分隔
    • 使用英文半角逗号分隔数据进行存储,不换行

缺点:数据中不能有英文逗号

  • 方式三:其他方式
    • 使用其他符号或符号组合分隔,建议采用特殊符号

缺点:需要根据数据特点定义,通用性较差

数据的处理
  • 存储→表示

  • 从空格分隔的文件中读入数据

  • 从特殊符号分隔的文件中读入数据

  • 一维数据的写入处理

    • 采用空格分隔方式将数据写入文件

    • 采用特殊分隔方式将数据写入文件

二维数据的格式化和处理

二维数据的表示
  • 使用列表类型:列表类型可以表达二维数据,

使用二维列表

  • 使用两层for循环遍历每个元素

外层列表中每个元素可以对应一行,也可以对应一列

  • 数据维度是数据的组织形式:
    • 一维数据:列表和集合类型
    • 二维数据:列表类型
CSV格式与二维数据存储

国际通用的一二维数据存储格式,一般.csv扩展名

每行一个一维数据,采用逗号分隔,无空行

Excel软件可读入输出,一般编辑软件都可以产生

如果某个元素缺失,逗号仍要保留

二维数据的表头可以作为数据存储,也可以另行存储

逗号为英文半角逗号,逗号与数据之间无额外空格

按行存或者按列存都可以,具体由程序决定

一般索引习惯:ls[row][column],先行后列

根据一般习惯,外层列表每个元素是一行,按行存

  • 二维数据的读入处理

  • 将数据写入CSV格式的文件:

  • 二维数据的逐一处理:

    • 采用二层循环:

练习:

  • 请描述数据维度的含义:

数据维度是数据 “立体”结构结构中独立坐标的数目, 是用数据描述事物或现象的

特征数目,如性别、地区、时间等都是维度。一维数据一般是线性结构,二维数据一般是表格

数据,高维数据采用对象方式组织。

  • JSON是一种什么样的数据格式:

JSON 是一种轻量级的数据交换格式,其实就是将一组数据转化为字符串。它包含

两种数据类型:对象和数组。

  • CSV能否支持高维数据表示:

可以支持,对 CSV 来说,高维相当于对数据分页,只要把几页数据放到一个 CSV

里,并在程序中约定好维度,就相当于实现了 CSV 的高维数据存储。

Logo

旨在为数千万中国开发者提供一个无缝且高效的云端环境,以支持学习、使用和贡献开源项目。

更多推荐