安全基础5 ---python

目录

python

定义

优点

缺点

python的数组

元组

python的类和对象

定义类 / 静态方法

python如何实现公开和私有?

为什么已经定义了私有变量,为什么还能访问并修改?

python的闭包

旅行者案例

python的列表生成式

斐波那契数列

可迭代对象和迭代器

python的高阶函数


python

定义

一个高层次的结合了解释性、编译性、互动性和面向对象的脚本语言。

优点

简单、易学、易读、易维护、速度快、灵活、免费开源、可移植性强、用途广泛、面向对象、可扩展、可扩充、可嵌入、库十分丰富

缺点

单行语句和命令行输出问题、运行速度慢

python的数组

#数组的基本使用
arr = ["123","abc","A","hello","DE","F"]
num = [2,5,12,9,24,66,17,8,32,44,22,6,9]
print(arr[3])
print(len(arr))

输出:
hello
6
#最大、最小、求和
print(min(num))
print(max(num))
print(sum(num))

输出:
2
66
256
#修改数组
arr[2] = "K"
print(arr)

输出:
['123', 'abc', 'K', 'hello', 'DE', 'F']
#删除数组中的字符串
del arr[5]
print(arr)

输出:
['123', 'abc', 'K', 'hello', 'DE']
#追加字符串
arr.append("VGS")
print(arr)

输出:
['123', 'abc', 'K', 'hello', 'DE', 'VGS']
#pop的使用
pop_item=arr.pop()
print("pop_item",pop_item)
print("arr",arr)

输出:
pop_item VGS
arr ['123', 'abc', 'K', 'hello', 'DE']
#数组的排序
print("原有arr:",arr)
arr.sort()
print("排序后的arr:",arr)
arr.reverse()
print("reverse后的arr:",arr)
print(sorted(arr))

输出:
原有arr: ['123', 'abc', 'K', 'hello', 'DE']
排序后的arr: ['123', 'DE', 'K', 'abc', 'hello']
reverse后的arr: ['hello', 'abc', 'K', 'DE', '123']
['123', 'DE', 'K', 'abc', 'hello']
#reverse的Treu和False
arr.sort(reverse=True)
print(arr)
arr.sort(reverse=False)
print(arr)

输出:
['hello', 'abc', 'K', 'DE', '123']
['123', 'DE', 'K', 'abc', 'hello']
#数组的循环索引:enumerate,可以循环出索引
print(arr)
for i, item in enumerate(arr):
    print(i,item)

输出:
['123', 'DE', 'K', 'abc', 'hello']
0 123
1 DE
2 K
3 abc
4 hello
#数组的切片
print(arr)
print("arr[1:3]:",arr[1:3])
print("arr[:2]:",arr[:2])
print("arr[3:]:",arr[3:])
print("循环切片:")
for i in arr[:4]:
    print(i)
print("复制切片:")
arr2=arr[:3]
print("arr2:",arr2)
arr2.append("987")
print("追加后的arr2:",arr2)

输出:
['123', 'DE', 'K', 'abc', 'hello']
arr[1:3]: ['DE', 'K']
arr[:2]: ['123', 'DE']
arr[3:]: ['abc', 'hello']
循环切片:
123
DE
K
abc
复制切片:
arr2: ['123', 'DE', 'K']
追加后的arr2: ['123', 'DE', 'K', '987']
#range(开始,结束,步长)生成数组,包括开始的数字,但是不包括结束的数字
num2=list(range(1,11,2))
print(num2)

输出:
[1, 3, 5, 7, 9]

元组

元组是一种特殊的数组(列表),是一种不可变的数组 。--->小括号()定义元组

元组是不可变的数组(列表)。也就是说,元祖中的每个值是固定的,是不可以变化的,如果给元祖中的某个值重新赋值,将会报错。

#元组
arr3=(1,3,5,7,9)
print(arr3)
#循环元组
for i in arr3:
    print(i)

输出:
(1, 3, 5, 7, 9)
1
3
5
7
9

python的类和对象

类:描述具有相同的属性和方法的对象的集合,定义了该集合中每个对象所共有的属性和方法。

--->  class 定义类、默认继承object

--->  import  类名:引用类

实例化:创建一个类的实例,类的具体对象。

---> 变量名 = 类名()

对象:通过类定义的数据结构实例。

方法:类中定义的函数。

---> def 定义方法、构造函数

调用构造函数:(实例化后的)变量.__ init __() , 显式的调用构造函数时,构造函数就变成一个普通函数,因为我们没有return value,所以函数默认返回none。构造函数不能也不需要返任何值

类变量:类变量在整个实例化的对象中是公用的。类变量定义在类中且在函数体之外。类变量通常不作为实例变量使用。

实例变量:在类的声明中,属性是用变量来表示的,这种变量就称为实例变量,实例变量就是一个用 self 修饰的变量。 

继承:即一个派生类(derived class)继承基类(base class)的字段和方法。

方法重写:如果从yin父类继承的方法不能满足子类的需求,可以对其进行改写,这个过程叫方法的覆盖(override),也称为方法的重写。

self的作用:保存对象属性 ,需要将数据传递到对象时,需要在对象中保存,若没有保存,对象找不到,就得不到想要的输出,此时需要self

if __name__=='__main__': #主函数调用 #

--> 可以作为程序的入口文件执行、也可以导入其他文件

定义类 / 静态方法

classmethod:定义类方法

staticmethod:定义静态方法,脱离其他对象,成为一个独立对象,不建议使用

python如何实现公开和私有?

公开和私有,可以定义属性修饰符:

  1. protected:受保护的--> 可以被子类调用
  2. private:私有的--> 只能自己用,仅提供一个接口,子类也用不了,但是可以在规范下修改
  3. public:公开--> 都可以调用

        python里的私有变量和私有方法都以双下划线开头 , 如果想要直接访问私有变量和私有函数,解释器会报错说类里没有这个属性 , 但是python的私有其实是伪私有,其实是python的名字改装在起作用,在类外访问类里的私有元素,变量和方法会被改名,加上_<类名>即可访问私有变量和私有方法。

  1. _类名: "单下划线 " 开始的成员变量叫做保护变量,意思是只有类实例和子类实例能访问到这些变量,需通过类提供的接口进行访问
  2. __类名: 类中的私有变量/方法名 " 双下划线 " 开始的是私有成员,意思是只有类对象自己能访问,连子类对象也不能访问到这个数据。
  3. __类名__ :系统定义名字,前后均有一个“双下划线” 代表python里特殊方法专用的标识,如 __init__()代表类的构造函数。
     

为什么已经定义了私有变量,为什么还能访问并修改?

“伪私有属性”:python的类中通过加双下划线来设置的“私有属性”其实是“伪私有属性”,原理是python编译器将加了双下划线的“属性名”自动转换成“类名属性名”。所以我们在外部用“属性名”访问私有属性的时候,会触发AttributeError,从而实现“私有属性”的特性。但通过“类名属性名”也可以访问这些属性。所以简单的说只是新创建了一个属性而已,并没有访问到私有变量

python的闭包

1、闭包=函数+环境变量

函数定义时候-->注意:环境变量一定要在定义函数的外部而且不能是全局变量

2、闭包=函数+自由变量的引用

什么是自由变量/环境变量(free variables)?

       在一个函数中,如果某个变量既不是在函数内部创建的也不属于函数的形参,并且它也不是全局变量(global variables), 那么这个变量对该函数来说就是自由变量,一定要定义到函数的外部。

3、closure函数的使用:

  • co_freevars:打印自由变量的key
  • cell_contents:打印自由变量的value
#python的闭包
def test1():
    a=9
    def test2(x):
        return a*x*x
    return test1
a=2
d=test1()
print(d.__closure__)
print(test1())

输出:
None
<function test1 at 0x000001F500B19310>

注意:返回函数不要引用任何循环变量,或者后续会发生变化的变量。(因为循环变量还没执行,需要执行时已经循环完了,所以得到错误的结果)

旅行者案例

X=0 -->代表起点-->每走一步加1

要求编写一个函数要求不断调用该函数求的旅行者的步数example:

  • 如果走3步 result = 3
  • 接着走4步 result = 7
  • 接着走8步 result = 15

1、使用非闭包解决:

#旅行者非闭包解决
t=0
def wk(step):
    global t
    new_t=t+step
    t=new_t
    return t
print(wk(1))
print(wk(4))
print(wk(8))

输出:
1
5
13

2、使用闭包解决:

def ft():
    t=0
    def wk(step):
        nonlocal t
        new_t=t+step
        t=new_t
        return t
    return wk

python的列表生成式

列表生成式:是一种基于其他iterable创建列表的方法。这种方法将整个输出列表加载到内存中,对于中小型的列表,这个是可取的,它可以使操作更快

  • 只要把一个列表生成式的[]改成(),就创建了一个generator
  • generator保存的是算法-->每次调用next(g),就计算出g的下一个元素的值,直到计算到最后一个元素,没有更多的元素时,抛出StopIteration的错误
  • 我们需要用for来调用直到计算到最后一个元素,没有更多的元素时,for可以将StopIteration捕获处理,不显示错误信息
  • 因为生成器也是一个可迭代对象

斐波那契数列

#斐波那契数列
def fb(max):
    n,a,b=0,0,1
    while n<max:
        a,b=b,a+b
        n+=1
        print(a)
    return 'done'
f=fb(7)
print(f)

输出:
1
1
2
3
5
8
13
done

注意:要把fib函数变成generator函数,只需要把print(a)改为yield a就可以了-->函数加上yield关键词就可以变成一个生成器

可迭代对象和迭代器

可迭代对象(iterable):可以被for循环的数据,如:字符串(str)、列表(list)、元组(tuple)、字典(key-value)、set(可直接去重)、生成树对象

iter()/ __ iter __() 函数:可以将可迭代对象变成迭代器

生成器yield[] ,()

生成器:itertor>iterable

python中的Iterator包可以测试是否是可迭代对象

python的高阶函数

高阶参数:把函数作为参数传入

lambda:匿名函数

f = lambda x, y : x + y
print(f(2,3))

输出:
5

map(函数名,需要处理的值):函数式编程,可以接收一个函数作为参数,然后将列表的值一个个放入函数中

line=map(lambda x: x*x,list(range(1,100,10)))
print(list(line))

输出:
[1, 121, 441, 961, 1681, 2601, 3721, 5041, 6561, 8281]

reduce(函数,可迭代对象):每次计算的结果作为下一次计算的参数值。

from functools import reduce
test= reduce(lambda x,y: x+y, list(range(8))[2::4])
print(test)

输出:
8

filter:过滤函数,满足要求的值留下--》仅处理符合条件(true)的值

test= filter(lambda x : True if x == 3 else False, [2,4,3,6,3,6,4,2,5,4,5,3,2,5,3,2,4,3])
print(list(test))

输出:
[3, 3, 3, 3, 3]

sorted :排序函数,可以加绝对值(key=abs)、小写字母(key=str.lower)、大写字母(key=str.upper)打印key/value值:打印索引:将value改成key,其中value打印为key值,key打印为索引。

a = sorted([2,-3,6,-9,10,-16,21], key=abs)
b= sorted(["abc","ann","ling","suxi"], key=str.lower)
c = sorted(["abc","ann","ling","suxi"], key=str.upper)
print(a)
print(b)
print(c)

输出:
[2, -3, 6, -9, 10, -16, 21]
['abc', 'ann', 'ling', 'suxi']
['abc', 'ann', 'ling', 'suxi']

decorator:装饰器,真正的业务逻辑并不在decorator里面,而是在wrapper里面。我们在wrapper外面包裹decorator实现不改变原有函数,增加新功能,看起来就像wrapper被decorator装饰一样。

import time
def decorator(func):
    def wrapper():
        print(time.time())
        func()
    return wrapper
def demo():
    print('测试')
f = decorator(demo)
f()

输出:
1658481879.3364596
测试

注意:

  1. 当函数没有返回值的时候,print返回的值为none
  2. python中自定义的函数不能和系统内的重名
  3. 默认参数必须在非默认参数之后
  4. 对自由变量赋值时/需要修改局部变量时,会报错,因为局部变量没有初始化,这个时候需要先声明
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值