python学习之路python基础(下)

admin 2022年3月17日07:27:57评论41 views字数 14474阅读48分14秒阅读模式

0x00 简单介绍Python的算法

1. 算法

  是指解题方案(一种问题的解决方案)准确而完整的描述,是一系列解决问题的清晰指令

range(4) ===> 0,1,2,3


2. 选择排序

a = [5,7,8,3,1]for j in range(len(a)-1):for i in range(j,len(a)-1):if a[j] > a[i+1]:a[j],a[i+1] = a[i+1],a[j]print(a)


3. 冒泡排序(省时间优化)

b = [5,7,8,3,1]for j in range(len(b)-1):swap = Falsefor i in range(len(b)-j-1):if b[i] > b[i+1]:b[i],b[i+1] = b[i+1],b[i]swap = Trueif swap == False:breakprint(b)


4.时间复杂度和空间复杂度(判断一个算法是否优秀的标准)

python学习之路python基础(下)

 

0x01 Flask制作一个Web应用

1. Flask框架介绍:(微框架)

@函数修饰符:在不修改原代码的同时,扩展函数能力@app.route('/') 函数修饰符可使下面的函数内容输出到网页pip install flask -i https://mirrors.aliyun.com/pypi/simple#flask_testfrom flask import Flaskapp = Flask(__name__) @app.route('/') #函数修饰符def first_flask():      return "hello"app.run()

 

2. 应用案例

需要建一个符合Flask框架要求的文件夹子,里面包含:static文件夹(存储静态文件);tenplates文件夹(存放模板文件)

#flask_testfrom flask import Flask,render_template #渲染模板app = Flask(__name__)@app.route('/hello')def first_flask():return "hello"@app.route('/enter')def enter_page():return render_template('enter.html',the_title='主页',)#return输出内容当三对引号时可插入多行,可换行app.run(debug=True)


3. Jinja介绍

Jinja是一种以Django模板为模型的,现代且设计友好的Python模板语言。借助可选的沙盒模板执行环境,它可以快速,广泛地使用并且安全:

<title>{% block title %}{% endblock %}</title><ul> {% for user in users %}    <li><a href="{{ user.url }}">{{ user.username }}</a></li>{% endfor %}</ul>

特征:

· 沙盒执行

· 强大的HTML自动转义系统,可防止XSS

· 模板继承

· 及时编译为最佳python代码

· 可选的提前模板编译

· 易于调试。例外的行号直接指向模板中的正确行。

· 可配置语法


4. 完整项目python部分

#flask_testimport area as areafrom flask import Flask,render_template,request #渲染模板import mathimport reapp = Flask(__name__)@app.route('/hello')def first_flask():return "hello"@app.route('/enter')def enter_page():return render_template('enter.html', the_title='主页',)@app.route('/area',methods=['POST'])def area_page():radius = request.form['radius']if radius == '' or radius.isspace==None:radius = 0if re.match('([0-9]|.){'+str(len(radius))+'}',radius) == None:radius = 0area = round(math.pi*float(radius)**2,3)return render_template('area.html', the_radius=radius, the_area=area,)app.run(debug=True)


0x02 存储数据

1. 文件存储

   文件==》打开(open),写(read/write),关闭(close)==>凡是打开后都要关闭

f=open('1.txt','r',encoding='utf-8')print(f.read())f.close()


    优化后:变得更简洁优雅,可自动close

with open('1.txt','r',encoding='utf-8') as f:print(f.read())


    读写方式:

Character Meaning--------- ---------------------------------------------------------------'r' open for reading (default)'w' open for writing, truncating the file first'x' create a new file and open it for writing'a' open for writing, appending to the end of the file if it exists'b' binary mode't' text mode (default)'+' open a disk file for updating (reading and writing)

 

2. 数据库存储

·  数据库:更好的存储、管理数据

· 关系型数据库:采用了关系模型来组织数据的数据库,其以行和列的形式存储数据,以便于用户理解,关系型数据库这一系列的行和列被称为表,一组表组成了数据库


3. 文件读写的函数

①tell()概述

tell() 方法返回文件的当前位置,即文件指针当前位置。

语法

tell() 方法语法如下:

fileObject.tell()

返回值

返回文件的当前位置。

 

②seek()概述

seek() 方法用于移动文件读取指针到指定位置。

语法

seek() 方法语法如下:

fileObject.seek(offset[, whence])

参数

· offset -- 开始的偏移量,也就是代表需要移动偏移的字节数,如果是负数表示从倒数第几位开始。

· whence:可选,默认值为 0。给 offset 定义一个参数,表示要从哪个位置开始偏移;代表从文件开头开始算起,代表从当前位置开始算起,代表从文件末尾算起。

返回值

如果操作成功,则返回新的文件位置,如果操作失败,则函数返回 -1。

 

 4. 存储内容:

    ①表单信息: request.form

    ②服务器地址: request.remote_ addr

    ③客户端信息: request.user _agent

    ④返回结果:运算结果

5. 案例代码:

#flask_test 案例一import area as areafrom flask import Flask,render_template,request   #渲染模板import mathimport reapp = Flask(__name__)#def do_area(redius):#    return math.pi*float(redius)**2@app.route('/hello')def first_flask():    return "hello"@app.route('/enter')def enter_page():    return render_template('enter.html',                           the_title='主页',)@app.route('/area',methods=['POST'])def area_page():    radius = request.form['radius']    if radius == '' or radius.isspace == None:        radius = 0    if re.match('([0-9]|.){'+str(len(radius))+'}',radius) == None:        radius = 0    area = round(math.pi*float(radius)**2,3)    with open('log.txt','a') as f:        f.write(str(request.form)+','+request.remote_addr+','+str(request.user_agent)+','+str(area))        #print(request.form,request.remote_addr,sep='|',file=f)    return render_template('area.html',                           the_radius=radius,                           the_area=area,)@app.route('/file_out')def file_out_page():    log = []    with open('log.txt','r',encoding='utf-8') as out:        log = out.readlines()        return render_template('file_out.html')        return  str(log)if __name__=='__main__':    app.run(debug=True)


案例二:html{% extends "base.html" %}{% block body %}<table border="">    <tr>    <th>str(request.form)</th>    <th>request.remote_addr</th>    <th>str(request.user_agent)</th>    <th>str(area))</th>    </tr>    {% for x in file1 %}    <tr>        {% for i in x %}        <td>{{ i }}        </td>        {% endfor %}    </tr>{% endfor %}</table>{% endblock %}


案例二:python#flask_testimport area as areafrom flask import Flask,render_template,request   #渲染模板import mathimport reapp = Flask(__name__)#def do_area(redius):#    return math.pi*float(redius)**2@app.route('/hello')def first_flask():    return "hello"@app.route('/enter')def enter_page():    return render_template('enter.html',                           the_title='主页',)@app.route('/area',methods=['POST'])def area_page():    radius = request.form['radius']    if radius == '' or radius.isspace == None:        radius = 0    if re.match('([0-9]|.){'+str(len(radius))+'}',radius) == None:        radius = 0    area = round(math.pi*float(radius)**2,3)    with open('log.txt','a') as f:        f.write(str(request.form)+'~'+request.remote_addr+'~'+str(request.user_agent)+'~'+str(area))        #print(request.form,request.remote_addr,sep='|',file=f)    return render_template('area.html',                          the_radius=radius,                           the_area=area,)@app.route('/file_out')def file_out_page():    log = []    with open('log.txt','r',encoding='utf-8') as out:        log = out.readlines()        file = []        for i in log:            file.append(i.split('~'))        return render_template('file1_out.html',                               file1=file)        #print(log)        #return  str(log)if __name__=='__main__':    app.run(debug=True)



0x03 数据库管理数据

1. 使用Python内置的数据库SOLite:

     ①SQLite本身是C写, 所以体积小巧,占用资源低

     ②SQLite本身是C写,所以处理速度非常快

     ③SQLite已经发布SQLite 3版本

     ④SQLite3支持Windows/Linwx/Unix等主流操作系统

     ⑤Python 2.5.x版本默认内置SQLite3,无需单独安装配置,直接用

2.SQLite介绍

  SQLite是一个进程内的库,实现了自给自足的、无服务器的、零配置的、事务性的 SQL 数据库引擎。它是一个零配置的数据库,这意味着与其他数据库不一样,您不需要在系统中配置。

  就像其他数据库,SQLite 引擎不是一个独立的进程,可以按应用程序需求进行静态或动态连接。SQLite 直接访问其存储文件。

使用:

      $sqlite3 DatabaseName.db : 创建数据库      sqlite> .databases : 显示数据库      .help: 获取命令清单      .show:查看sqlite命令提示符的默认设置      .tables:查看表名      .schema sqlite_ master: 查看表概要      .quit: 退出

      

存储类

描述

NULL

值是一个 NULL 值。

INTEGER

值是一个带符号的整数,根据值的大小存储在 1、2、3、4、6 或 8 字节中。

REAL

值是一个浮点值,存储为 8 字节的 IEEE 浮点数字。

TEXT

值是一个文本字符串,使用数据库编码(UTF-8、UTF-16BE 或 UTF-16LE)存储。

BLOB

值是一个 blob 数据,完全根据它的输入存储。

  SQLite 的存储类稍微比数据类型更普遍。INTEGER 存储类,例如,包含 6 种不同的不同长度的整数数据类型。

3. MySQL

当遇到问题时==》? create table 查询创建数据表的用法

          ? contents 查看数据类型

  对比之下,插入多行时,用VALUE比较快根据所得出的结论,应该在插入单行的时候使用VALUES,在插入多行的时候使用VALUE

修改表中指定字段==》alter table log change column browser_string brower_string varchar(200);

#flask_testimport area as areafrom flask import Flask,render_template,request   #渲染模板import mathimport reimport pymysqlfrom DBcm import UseDatabaseapp = Flask(__name__)@app.route('/hello')def first_flask():    return "hello"@app.route('/enter')def enter_page():    return render_template('enter.html',                          the_title='主页',)@app.route('/area',methods=['POST'])def area_page():    radius = request.form['radius']    if radius == '' or radius.isspace == None:        radius = 0    if re.match('([0-9]|.){'+str(len(radius))+'}',radius) == None:        radius = 0    area = round(math.pi*float(radius)**2,3)    '''    mysql学习    '''    #连接数据库    conn = pymysql.connect('127.0.0.1', 'root', 'root', 'test')    cursor = conn.cursor()    # 数据库文件读写    sql = '''insert into mysql1(radius,browser_string,area) values(%s,%s,%s)'''    cursor.execute(sql, (float(radius), str(request.user_agent), str(area)))    conn.commit()    #关闭连接    cursor.close()    conn.close()    return render_template('area.html',                          the_radius=radius,                          the_area=area, )@app.route('/file_out')def file_out_page():    # 连接数据库    conn = pymysql.connect('127.0.0.1', 'root', 'root', 'test')    cursor = conn.cursor()    # 数据库文件读写    sql="""select radius,browser_string,area from mysql1"""    cursor.execute(sql)    result = cursor.fetchall()    conn.commit()    # 关闭连接    cursor.close()    conn.close()    return render_template('file1_out.html',                           file1=result)if __name__=='__main__':    app.run(debug=True)


0x04 面向对象

1.面向对象:(封装,继承,多态,重载)对象=属性(静态)+行为(动态=》方法,函数)

      在现实世界中存在各种不同形态的事物,这些事物之间存在着各种各样的联系。在程序中使用对象来映射现实中的事物,使用对象间的关系来描述事物之间的联系,这种思想就是面向对象。

2.类的定义:class类名,类的属性,类的方法

      类是由3部分组成的:

    ●类的名称:类名,首字母必须大写,比如Person。

    ●类的属性:一组数据,比如性别。

    ●类的方法:允许进行操作的方法,比如说话。

'''类'''class Man:    weight = 120        #类的属性    def __init__(self,n,a,h):     #可以理解为构造函数        self.name = n        self.age = a        self.height = h    def hello(self):        print("你好,我是***"+self.name)class Boy(Man):    def __init__(self,n,a,h):     #可以理解为构造函数,初始化        self.name = n        self.age = a        self.height = h    def hello(self):        print("你好,我是---"+self.name)    @staticmethod   #静态方法:不能访问对象的东西,类方法访问不需要实例化    def eat():        print('恰饭!!!')    @property       #方法属性  ==>   把方法属性化,调用不用加括号    def a(self):        return self.age        #print('我的年龄:',self.age)lai = Man('lai',22,170)     #多态bob = Boy('BOB',18,120)print(bob.a)Boy.eat()Man.hello(lai)Boy.hello(lai)


3. 构造方法:

    ●构造方法指的是_ init_ 方法。==>初始化

    ●当创建类的实例的时候,系统会自动调用构造方法,从而实现对类进行初始化的操作。

析构方法:

    ●当删除一个对象来释放类所占用资源的时候,Python解释器默认会调用另外一个方法,这个方法就是___del__ ( )方法。

    ●__del__ 方法被称为析构方法。

    C++需要手动析构;Python,Java会虚拟机自动销毁

 4. self的使用:

    ●在方法的列表中,第1个参数永远都是self。

    ●self的字面意思是自己, 我们可以把它当做C+ +里面的this指针理解,表示的是对象自身。

    ●当某个对象调用方法的时候,Python解释器 会把这个对象作为第1个参数传给self,开发者只需要传递后面的参数就可以了。

5. 运算符重载

    运算符重载是通过实现特定的方法使类的实例对象支持Python的各种内置操作。例如: +运算符是类里提供的__add__ 这个函数,当调用+实现加法运算的时候,实际上是调用了__add__ 方法。

#重载是根据传入的参数个数的不同,会执行不同的函数

class Vector:   def __init__(self, a, b):      self.a = a      self.b = b    def __str__(self):      return 'Vector (%d, %d)' % (self.a, self.b)      def __add__(self,other):      return Vector(self.a + other.a, self.b + other.b) v1 = Vector(2,10)v2 = Vector(5,-2)print (v1 + v2)


#重写是,子类继承父类后,子类对父类部分方法和函数进行重新书写

class Parent:        # 定义父类   def myMethod(self):      print ('调用父类方法') class Child(Parent): # 定义子类   def myMethod(self):      print ('调用子类方法') c = Child()          # 子类实例c.myMethod()         # 子类调用重写方法super(Child,c).myMethod() #用子类对象调用父类已被覆盖的方法


6.索引和分片重载

跟索引相关的重载方法包括如下3个:

    ●__getitem__ : 索引、分片;

    ●__setitem__ :索引赋值;

    ●__delitem__ :索引和分片删除。

    ①__getitem__方法

    在对实例对象执行索引、分片或者for迭代操作时,会自动调用__getitem__方法。通过此方法实现求值,对于序列类型,接受的键应为整数和切片对象。

#定义索引、分片运算符重载方法       

 def __getitem__(self, index):                return self.data[index]

    ②__setitem__方法

    通过赋值语句给索引或者分片赋值时,调用__setitem__方法实现对序列对象的修改。          

def __setitem__ (self, index, value):             self.data[index] = value

    ③__delitem__方法

    这个方法在对对象的组成部分使用__del__语句的时候被调用,应删除与key相关联的值。同样,仅当对象可变的时候,才需要实现这个方法。


0x05 上下文管理协议

1. 定义:一个包装任意代码的对象,适合“建立、处理、清理”模式的代码

with open( 'test.txt','w')as f:f.write( '我想做个好人! '

作用:①提高代码的复用率

           ②让代码看起来更优雅

           ③让代码更可读

2. 协议的规则:在一个类里实现了__enter__和__exit__的方法

"""处理数据库上下文的管理器"""import pymysqlclass UseDatabase:    def __enter__(self):        # 连接数据库        self.conn = pymysql.connect('127.0.0.1', 'root', 'root', 'test')        self.cursor = self.conn.cursor()        return self.cursor      #无return,就没办法使用当前对象    def __exit__(self, exc_type, exc_val, exc_tb):  #关闭退出时可能发出异常,处理异常        self.conn.commit()        self.cursor.close()        self.conn.close()


#flask_testimport area as areafrom flask import Flask,render_template,request   #渲染模板import mathimport reimport pymysqlfrom DBcm import UseDatabaseapp = Flask(__name__)@app.route('/hello')def first_flask():    return "hello"@app.route('/enter')def enter_page():    return render_template('enter.html',                           the_title='主页',)@app.route('/area',methods=['POST'])def area_page():    radius = request.form['radius']    if radius == '' or radius.isspace == None:        radius = 0    if re.match('([0-9]|.){'+str(len(radius))+'}',radius) == None:        radius = 0    area = round(math.pi*float(radius)**2,3)    '''    mysql学习    '''    with UseDatabase() as cursor:        # 数据库文件读写        sql = '''insert into mysql1(radius,browser_string,area) values(%s,%s,%s)'''        cursor.execute(sql, (float(radius), str(request.user_agent), str(area)))    return render_template('area.html',                                the_radius=radius,                                the_area=area, )@app.route('/file_out')def file_out_page():    with UseDatabase() as cursor:        # 数据库文件读写        sql="""select radius,browser_string,area from mysql1"""        cursor.execute(sql)        result = cursor.fetchall()    return render_template('file1_out.html',                           file1=result)if __name__=='__main__':    app.run(debug=True)


3.生成器函数实现上下文管理器:

生成器函数(带有yield的函数),结合装饰器===》与return不同,yield是返一个函数,return是返回值

 

0x06 函数修饰符

函数修饰符作用:为现有函数增加功能而不必修改现有函数代码

    ①修饰符是一个函数

    ②修饰符取被修饰函数为参数

    ③修饰符返回一个新函数

    ④修饰符维护被修饰函数的签名(参数)

 

"""函数修饰符"""#定义函数修饰符from functools import wrapsdef test_decorator(func):  @wraps(func)                           #可以维护被修饰函数的属性    def wrapper(*args,**kwargs):           #参数长度不固定,一个关键字=》*args      print("****开始****")               #参数为键值对,接收任意多个关键字参数        func(*args,**kwargs)        print('****结束****')    return wrapper@test_decoratordef hello(name,age):    print('你好呀,小哥哥,我是:',name,age)hello(name='lily',age=12


0x07 异常处理

1. 异常类

· 所有异常都是基类Exception的成员,它们都定义在exceptions模块中。

· 如果这个异常对象没有进行处理和捕捉,程序就会用所谓的回溯(traceback, 一种错误信息)终止执行,这些信息包括错误的名称(例如NameError)、原因和错误发生的行号。

· 语法错误。索引错误。keyError。文件名不存在。


2. 关键字及案例

try 语句按照如下方式工作;

· 首先,执行 try 子句(在关键字 try 和关键字 except 之间的语句)。

· 如果没有异常发生,忽略 except 子句,try 子句执行后结束。

· 如果在执行 try 子句的过程中发生了异常,那么 try 子句余下的部分将被忽略。如果异常的类型和 except 之后的名称相符,那么对应的 except 子句将被执行。

· 如果一个异常没有与任何的 except 匹配,那么这个异常将会传递给上层的 try 中。

    一个 try 语句可能包含多个except子句,分别来处理不同的特定的异常。最多只有一个分支会被执行。处理程序将只针对对应的 try 子句中的异常进行处理,而不是其他的 try 的处理程序中的异常。

"""异常案例:division by zero"""number = int(input('输入被除数'))try:    x = 1/numberexcept Exception as e:    print(e)"""异常案例:unsupported operand type(s) for /: 'int' and 'str'"""try:    number = input('输入被除数')    x = 1/numberexcept Exception as e:  print(e)"""异常案例"""number = int(input('输入被除数'))try:    x = 1/numberexcept Exception as e:    print(e)else:    print("否则")           #没错会执行finally:    print("执行完成")       #不管执行有无错误,都会执行


3. raise:手动抛出异常

    raise语法格式如下:raise [Exception [, args [, traceback]]]

    raise 唯一的一个参数指定了要被抛出的异常。它必须是一个异常的实例或者是异常的类(也就是 Exception 的子类)。如果你只想知道这是否抛出了一个异常,并不想去处理它,那么一个简单的 raise 语句就可以再次把它抛出。

>>> try:        raise NameError('HiThere')    except NameError:        print('An exception flew by!')        raise   An exception flew by!Traceback (most recent call last):  File "<stdin>", line 2, in ?NameError: HiThere


4. assert:断言 ===> assert 1==3

    assert(断言)用于判断一个表达式,在表达式条件为 false 的时候触发异常。

    断言可以在条件不满足程序运行的情况下直接返回错误,而不必等待程序运行后出现崩溃的情况,例如我们的代码只能在 Linux 系统下运行,可以先判断当前系统是否符合条件

    assert expression <==> if not expression:                                 raiseAssertionError

assert 后面也可以紧跟参数:

>>> assert True     # 条件为 true 正常执行>>> assert False    # 条件为 false 触发异常Traceback (most recent call last):  File "<stdin>", line 1, in <module>AssertionError>>> assert 1==1    # 条件为 true 正常执行>>> assert 1==2    # 条件为 false 触发异常Traceback (most recent call last):  File "<stdin>", line 1, in <module>AssertionError>>> assert 1==2, '1 不等于 2'Traceback (most recent call last):  File "<stdin>", line 1, in <module>AssertionError: 1 不等于 2


5. 自定义异常:

可以通过创建一个新的异常类来拥有自己的异常。异常类继承自 Exception 类,可以直接继承,或者间接继承。当创建一个模块有可能抛出多种不同的异常时,一种通常的做法是为这个包建立一个基础异常类,然后基于这个基础类为不同的错误情况创建不同的子类


6. 异常抛出原则:

精确:只对可能产生异常的代码,进行异常处理

抽象级别:  抛出的异常与自己的抽象级别对应

with语句更优雅: 上下文管理器更优雅处理异常


0x08 总结

    因为才接触Python,想要记录的太多了,导致文章篇幅很大,感谢愿意看到文末的你啦。。。程序猿哥哥说学习一门语言,最重要的是学习如何去使用他的库、类。。好好的读懂如何利用API文档比买很多其他的书都还来的有用。。

    奉上所有python的学习资料(视频和编程语言api文档的链接),后台回复“python学习包”,即可获得啦~~~

    学安全,菜是原罪。。。所以,一起加油吧,顶端相见



本文始发于微信公众号(凌晨安全):python学习之路----python基础(下)

  • 左青龙
  • 微信扫一扫
  • weinxin
  • 右白虎
  • 微信扫一扫
  • weinxin
admin
  • 本文由 发表于 2022年3月17日07:27:57
  • 转载请保留本文链接(CN-SEC中文网:感谢原作者辛苦付出):
                   python学习之路python基础(下)https://cn-sec.com/archives/497423.html

发表评论

匿名网友 填写信息