python概念及语法

概念

编译器与解释器

编译器是把源程序的每一条语句都编译成机器语言,并保存成二进制文件,这样运行时计算机可以直接以机器语言来运行此程序,速度很快;它把源代码转换成目标机器的CPU指令

解释器则是只在执行程序时,才一条一条的解释成机器语言给计算机来执行,所以运行速度是不如编译后的程序运行的快的。解释后转换成字节码,运行在虚拟机上,解释器执行中间代码。

这是因为计算机不能直接认识并执行我们写的语句,它只能认识机器语言(是二进制的形式)。

编译型语言与解释型语言

  • 编译型
    优点:编译器一般会有预编译的过程对代码进行优化。因为编译只做一次,运行时不需要编译,所以编译型语言的程序执行效率高。可以脱离语言环境独立运行。
    缺点:编译之后如果需要修改就需要整个模块重新编译。编译的时候根据对应的运行环境生成机器码,不同的操作系统之间移植就会有问题,需要根据运行的操作系统环境编译不同的可执行文件。

  • 解释型
    优点:有良好的平台兼容性,在任何环境中都可以运行,前提是安装了解释器(虚拟机)。灵活,修改代码的时候直接修改就可以,可以快速部署,不用停机维护。

    缺点:每次运行的时候都要解释一遍,性能上不如编译型语言。

低级语言与高级语言

  • 低级语言

    面向机器的语言,包括机器语言、汇编语言

    不同的机器不能通用,不同的机器需要不同的机器指令或者汇编程序

  • 高级语言

    接近自然语言和数学语言的计算机语言

    高级语言首先要书写源程序,通过编译程序把源程序转换成机器指令的程序

    人们只需要关心怎么书写源程序,针对不同机器的编译的事交给编译器处理

语言越高级,越接近人类的自然语言和数学语言。语言越低级,越能让机器理解。高级语言和低级语言之间需要一个转换的工具,就是编译器或解释器。

动态语言和静态语言

  • 动态类型语言:动态类型语言是指在运行期间才去做数据类型检查的语言,也就是说,在用动态类型的语言编程时,永远也不用给任何变量指定数据类型,该语言会在你第一次赋值给变量时,在内部将数据类型记录下来。Python和Ruby就是一种典型的动态类型语言,其他的各种脚本语言如VBScript也多少属于动态类型语言。

  • 静态类型语言:静态类型语言与动态类型语言刚好相反,它的数据类型是在编译其间检查的,也就是说在写程序时要声明所有变量的数据类型,C/C++是静态类型语言的典型代表,其他的静态类型语言还有C#、JAVA等。

强类型定义语言和弱类型定义语言

  • 强类型语言:不同类型之间操作,必须先强制类型转换为同一类型。print(‘a’+1)
  • 弱类型语言:不同类型间可以操作,自动隐式转换,JavaScript中console.log(1+’a’)

基础语法

  • 注释:# 标注的文本

  • 数字:

    • 整数,不区分long和int。可使用二进制、十进制、十六进制。bool(布尔)有两个值True和False
    • 浮点数:1.2、3.1415、-0.12、1.46e9等价于1.46*10的9次方
    • 复数:1+2j
  • 字符串:

    • 使用’ “ 单双引号引用的字符的序列
    • ‘’’和””” 单双三引号,可以跨行、可以在其中自由的使用单双引号
    • 在字符串前面加上r或R前缀,表示该字符串不做特殊的处理
  • 转义序列

    • \\ \t \r \n \‘ \“
    • 前缀r,把里面的所有字符当普通字符对待
  • 缩进

    • 未使用C等语言的花括号,而是采用缩进的方式表示层次关系
    • 约定使用4个空格缩进
  • 续行

    • 在行尾使用\
    • 如果使用各种括号,认为括号内是一个整体,内部跨行不用\
  • 标识符

    1. 一个名字,用来指代一个值
    2. 只能字母、下划线和数字
    3. 只能以字母或下划线开头
    4. 不能是python的关键字,如def、class就不能作为标识符
    5. python是大小写敏感的
    • 约定:
      • 不允许使用中文
      • 不允许使用歧义单词,如class_
      • 在python中不要随便使用下划线开头的表示符
  • 常量

    • 一旦赋值就不能改变值的标识符
    • python中无法定义常量
  • 字面常量

    • 一个单独的量,如12、”abc”、’234531.03e-9’
  • 变量

    • 赋值后,可以改变值的标识符

运算符

算数运算符

运算符 描述 实例
+ 两个对象相加 a + b输出结果30;a=10, b=20
- 得到负数或是一个数减去另一个数 a - b输出结果-10
* 两个数相乘或是返回一个被重复若干次的字符串 a * b输出结果200
/ x除以y b / a输出结果2
% 返回除法的余数 b % a输出结果0
** 返回x的y次幂 a ** b为10的20次方,输出结果1000000000000000000
// 返回商的整数部分 9 // 2输出结果4,9.0//2.0输出结果4.0

比较运算符

运算符 描述 实例
== 比较两个对象是否相等 (a == b)返回False
!= 比较两个对象是否不等 (a != b)返回true
<> 比较两个对象是否不等 (a <> b)返回true。这个运算符类似!=
> 返回x是否大于y,返回一个bool值 (a > b)返回False;4>3>2或4>mynumber>=1是链式比较操作符
< 返回x是否小于y。所有比较运算符返回1表示真,返回0表示假。这分别与特殊的变量True和False等价。注意,这些变量名的大写。 (a < b)返回true
>= 返回x是否大于等于y (a >= b)返回False
<= 返回x是否小于等于y (a <= b)返回true

赋值运算符

运算符 描述 实例
= 简单的赋值运算符 c = a+b将a + b的运算结果赋值为c
+= 加法赋值运算符 c += a等效于c = c + a
-= 减法赋值运算符 c -= a等效于c = c - a
*= 乘法赋值运算符 c *= a等效于c = c * a
/= 除法赋值运算符 c /= a等效于c = c / a
%= 取模赋值运算符 c %= a等效于c = c % a
**= 幂赋值运算符 c **= a等效于c = c ** a
//= 取整除赋值运算符 c //= a等效于c = c // a

逻辑运算符

短路运算符,可以把and当作乘法,把or当作加法,非是取反。and:如果第一个表达式为False,后面就没有必要计算了,这个逻辑表达式一定是False;or:如果第一个表达式为True,后面没有必要计算了,这个逻辑表达式一定是True

运算符 描述 实例
and 布尔“与”,如果x为False,x and y返回False,否则它返回y的计算值 (a and b)返回true
or 布尔“或”,如果x是True,它返回True,否则它返回y的计算值 (a or b)返回true
not 布尔“非”,如果x为True,返回False。如果x为False,它返回True not(a and b)返回false

成员运算符

运算符 描述 实例
in 如果在指定的序列中找到值返回True,否则返回False x在y序列中,如果x在y序列中返回True
not in 如果在指定的序列中没有找到值返回True,否则返回False x不在y序列中,如果x不在y序列中返回True

身份运算符

运算符 描述 实例
is is是判断两个标识符是不是引用自一个对象 x is y,如果id(x)等于id(y),is返回结果1
is not is not是判断两个标识符是不是引用自不同对象 x is not y,如果id(x)不等于id(y),is not返回结果1

位运算符

运算符 描述 实例
& 按位与运算符 (a & b)输出结果12,二进制解释:0000 1100。只有1和1相与得1,其他相与都是0
I 按位或运算符 (a I b)输出结果61,二进制解释:0011 1101
^ 按位异或运算符 (a ^ b)输出结果49,二进制解释:0011 0001
~ 按位取反运算符 (~a)输出结果-61,二进制解释:1100 0011,在一个有符号二进制数的补码形式
<< 左移动运算符 a << 2输出结果240,二进制解释:1111 0000
>> 右移动运算符 a >> 2输出结果15,二进制解释:0000 1111

运算符优先级

算数运算符 > 位运算符 > 身份运算符 > 成员运算符 > 逻辑运算符

记不住,就用小括号

长表达式,多用括号,易懂、易读

原码、反码、补码、负数表示法

  • 原码

    5 => 0b101,1 => 0b1,-1 => -0b1,bin(-1)

  • 反码

    正数的反码与原码相同;负数的反码符号位不变其余按位取反

  • 补码

    正数的补码与原码相同;负数的补码符号位不变其余按位取反后+1;补码的补码就是原码

  • 负数表示法

    数字电路的CPU中的运算器实现了加法器,但是没有减法器,减法是转换成加法

    负数在计算机中使用补码存储,-1的补码为1111 1111

    5 - 1 => 5+(-1)直觉上是0b101-0b1,其实计算机中是0b101+0b11111111,溢出位舍弃

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
例:5-1保存为二进制
0000 0101
# 5的二进制。原码是人比较习惯的方式,-0b1中的负号表示转换为二进制数字时在最高位是0还是1,1表示负号,0表示正号。-0b1是python中的写法。-0b1也就是原码
1111 1111
# -1的二进制,因为计算机中保存的都是补码,而正数的原码与补码一样,所以上面的5不会变。-1的二进制是1000 0001,转换为补码后,除最高位的符号位不变外,还要加1,就是1111 1110 + 1,所以最后就是1111 1111
1 0000 0100
# 这是5和-1的二进制相加后的结果,因为最高位的1溢出了,所以舍弃,最后就变成了0000 0100,也就是4了

例:~12为什么是-13
0000 1100
# 这是12的二进制
1111 0011
# 这是对12的二进制取反后的数,但最高位是1表示负数,并且保存在计算机中的应该是数字的补码,所以要取这个负数的补码
1000 1101
# 这是对上面二进制数取的补码,因为上面表示负数,所以按照最高位不变最后加1的原则,取出的二进制数就是这个数,转换为十进制数就是-13了。

内存管理

变量无须事先声明,也不需要指定类型

编程中一般无须关心变量的存亡,也不用关心内存的管理

python使用引用 计数记录所有对象的引用数。当对象引用数变为0,它就可以被垃圾回收(GC)了。

计数增加:赋值给其它变量就增加引用计数,例如:x=3;y=x

计数减少:函数运行结束时,局部变量就会被自动销毁,对象引用计数减少。变量被赋值给其它对象。例如:x=3;y=x;x=4

程序控制

  • 顺序

    按照先后顺序一条条执行

  • 分支

    根据不同的情况判断,条件满足执行某条件下的语句

  • 循环

    条件满足就反复执行,不满足就不执行或不再执行

单分支结构

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
if语句
if condition:
代码块
# condition必须是一个bool类型,这个地方有一个隐式转换bool(condition)
if 1 < 2:
print('1 less than 2')
# 代码块:类似于if语句的冒号后面的就是一个语句块

=======================================================================================
真值表
""
"string"
0
>=1
<=-1
()空元组 假
[]空列表 假
{}空字典 假
None
=======================================================================================

三目运算

1
2
3
语法:真值if条件else假值
x if(x>y) else y
print((x if (x>y) else y) if ((x if (x>y) else y)>z) else z)

多分支结构

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
if...elif...else语句
if condition1:
代码块1
elif condition2:
代码块2
elif condition3:
代码块3
... ...
else:
代码块

例:
a = 5
if a < 0:
print('negative')
elif a == 0:
print('zero')
else:
print('positive')

分支嵌套

1
2
3
4
5
6
7
8
9
10
11
例:
score = 80
if score < 0:
print('wrong')
else:
if sore == 0:
print('egg')
elif score <= 100:
print('right')
else:
print('too big')

while循环

1
2
3
4
5
6
7
8
9
10
11
while condition:
block
# 当条件满足即condition为True,进入循环体,执行block

例:
flag = 10
while flag:
print(flag)
flag -= 1
# lag是标记,while flag也就是while为真,flag会递减,等flag等于0时,while就会退出循环了
# while true是死循环,因为条件永远为真,不会变成假。如果 改为-10也会是死循环,可以使用return退出死循环

for循环

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
for element in iteratable:
block
# 当可迭代对象中有元素可以迭代,进入循环体,执行block

例:
for i in range(10):
print(i+1)
# range()函数类似seq命令,range(10)可以输出从0到9,共10个数字
# iteratable表示迭代的,element表示元素。

In [1]: range?
Init signature: range(self, /, *args, **kwargs)
Docstring:
range(stop) -> range object
range(start, stop[, step]) -> range object

Return an object that produces a sequence of integers from start (inclusive)
to stop (exclusive) by step. range(i, j) produces i, i+1, i+2, ..., j-1.
start defaults to 0, and stop is omitted! range(4) produces 0, 1, 2, 3.
These are exactly the valid indices for a list of 4 elements.
When step is given, it specifies the increment (or decrement).
Type: type
Subclasses:
# range?可以查看帮助

In [4]: for i in range(3,5):
...: print(i)
...:
3
4
# 只会输出3和4

In [5]: for i in range(2,6,2):
...: print(i)
...:
2
4
# 还可以加上步长

循环continue语句

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
中断当前循环的当次执行,继续下一次循环
例:
In [7]: for i in range(10):
...: if not i%2:
...: print(i)
...:
0
2
4
6
8
# 这里会打印偶数是因为range中的数字与2取余后,如果是0就表示假,1表示真,但取余前加了not,所以假就变成了真,所以打印的是偶数,如果不加not,那么就会打印所有奇数。

In [9]: for i in range(0,10,2):
...: print(i)
...:
0
2
4
6
8
# 直接使用range()函数就可以打印奇偶数

In [10]: for i in range(0,10):
...: if i & 1:
...: continue
...: print(i)
...:
0
2
4
6
8
# range()函数内的数字和1按位与,如果为真,也就是1,就会中断当前循环,如果为假就会打印i

循环break语句

1
2
3
4
5
6
7
8
9
终止当前循环,跳出循环
例:计算1000以内的被7整除的前20个数(for循环)
count = 0
for i in range(0,1000,7):
print(i)
count += 1
if count == 20:
break
# range必须从0开始,如果从1开始,那么永远到不了7的整数倍。但这样也会打印0

continue和break语句总结

  • continue和break是循环的控制语句,只影响当前循环,包括while、for循环
  • 如果循环嵌套,continue和break也只影响语句所在的那一层循环
  • continue和break不是跳出语句块,所以if cond: break不是跳出if,而是终止if外的break所在的循环

循环else子句

1
2
3
4
5
6
7
8
9
10
# 如果循环正常的执行结束,就执行else子句;如果使用break终止,else子句不会执行
while condition:
block
else:
block

for element in iteratable:
block
else:
block

练习

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
1. 输入2个数字,输出最大数
a = input('>>>')
b = input('>>>')
while a == b:
print('请重新输入')
a = input('>>>')
b = input('>>>')
if a > b:
print(a)
else:
print(b)

2. 给定一个不超过5位的正整数,判断其有几位
# 使用input函数,例:input函数获取键盘输入,input([prompt])。input()是内建函数,返回的是字符串。下划线在ipython中是一个特殊的字符,表示上一次output的结果。
a = int(input('>>>'))
if a // 100000:
print('6位数')
elif a // 10000:
print('5位数')
elif a // 1000:
print('4位数')
elif a // 100:
print('3位数')
elif a // 10:
print('2位数')
elif a // 1:
print('1位数')

3. 给定一个不超过5位的正整数,判断该数的位数,依次打印出个位、十位、百位、千位、万位的数字

4. 打印一个连长为n的正方形

5.100内所有奇数的和(2500)

6. 判断学生成绩,成绩等级A~E。其中,90分以上为A,8089分为B,7079分为C,6069分为D,60分以下为E

7.15阶乘之和

8. 给一个数,判断它是否是素数(质数)。质数:一个大于1的自然数只能被1和它本身整除

9. 打印九九乘法表

10. 打印菱形

11. 打印100以内的斐波那契数列

12. 求斐波那契数列第101

13.10万内的所有素数
作者

John Doe

发布于

2019-02-15

更新于

2023-03-17

许可协议