首页 > 编程语言 >python基础理论小总结

python基础理论小总结

时间:2024-07-24 15:42:11浏览次数:15  
标签:总结 __ 函数 python 对象 json new 基础理论 序列化

1. python语言的特性

Python是一门解释型语言, 简单清晰,开源免费,跨平台,有大量第三方库辅助开发,支持面向对象与自动垃圾回收,方便与其他编程语言相互调用。

Python在数据采集、人工智能、WEB后台开发、自动化运维、测试等方向应用广泛。

2. 解释型语言和编译型语言的区别

  • 执行方式不同
    • 解释型语言:解释型语言的代码在运行时由解释器逐行读取并执行,不需要事先将整个程序编译成机器代码。
    • 编译型语言:编译型语言的代码在执行前需要通过编译器编译成机器代码(或者字节码),生成可执行文件。该可执行文件在运行时直接由操作系统加载和执行。
  • 开发和调试
    • 解释性语言:不需要编译过程,开发者可以快速编写和测试代码,调试过程也比较直观,因为代码的修改可以立即生效。
    • 编译型语言:开发过程包括编写代码、编译、链接和执行。调试时可能需要重新编译代码,调试流程相对解释型语言来说稍显复杂。
  • 性能
    • 解释型语言:解释型语言通常比编译型语言慢,因为每次执行代码时都需要进行解释,而编译型语言的代码在编译阶段已经转换成了机器代码。
    • 编译型语言:编译型语言通常运行速度更快,因为编译阶段已经将代码转换为高效的机器代码。不需要在运行时进行解释,因此性能更高。
  • 平台依赖性
    • 解释性语言:解释型语言的代码在不同平台上运行时,只需要有适配相应平台的解释器即可,无需针对每个平台分别编译。
    • 编译型语言:编译型语言的代码通常与具体的硬件和操作系统相关,不同平台可能需要不同的编译过程和生成不同的可执行文件。
  • 解释型语言的优点是开发周期短、跨平台能力强,适合快速开发和迭代。
  • 编译型语言的优点是执行效率高、优化能力强,适合对性能要求较高的应用。

3. python原生数据类型

  1. 整型(int):用于表示整数,例如 1, 100, -5 等。
  2. 浮点型(float):用于表示带有小数点的数字,例如 3.14, -0.001 等。
  3. 空值(None)
  4. 布尔型(bool):用于表示逻辑值,True 或 False。
  5. 字符串型(str):用于表示文本,例如 "hello", 'python' 等。
  6. 列表(list):用于存储多个元素的有序集合,可以通过索引访问和修改元素。
  7. 元组(tuple):类似于列表,但是一旦创建就不能被修改(不可变)。
  8. 集合(set):用于存储独一无二的元素,不支持重复元素,可以进行集合运算。
  9. 字典(dict):用于存储键值对的数据结构,通过键来快速查找对应的值。

4. python中哪些是可变类型,哪些是不可变类型,有什么区别

可变类型包括:

  1. 列表(list)
  2. 集合(set)
  3. 字典(dict)

不可变类型包括:

  1. 整型(int)
  2. 浮点型(float)
  3. 空值(None)
  4. 布尔型(bool)
  5. 字符串型(str)
  6. 元组(tuple)

区别

  • 可变性

    • 可变类型的是引用同一个对象,可以对内容进行修改,只是修改了其内容,并不会创建新的对象
    • 不可变修改类型一旦创建,其内容就不能更改。如果尝试修改不可变对象,将会创建一个新的对象。
  • 存储方式和性能

    • 可变类型通常使用更多的内存,因为它们支持动态的插入和删除操作,可能会导致频繁的内存分配和释放。
    • 不可变类型由于内容不可改变,可以被安全地共享和重用,这在多线程编程中尤为重要。
  • 哈希性

    • 可变类型一般是不可哈希的,因为其内容可以改变,如果用作字典的键或集合的元素会导致不一致性
    • 不可变类型通常是可哈希的,因为其值不会变化,可以用作字典的键或集合的元素。

5. 常用的数据结构有哪些?各自的特点?

  1. 列表(List)
    • 特点:有序、可变、可包含重复元素。
    • 使用场景:适合存储需要频繁修改(增删改查)的数据。
  2. 元组(Tuple)
    • 特点:有序、不可变、可包含重复元素。
    • 使用场景:适合存储不需要修改的数据,具有更高的访问速度。
  3. 集合(Set)
    • 特点:无序、不重复、可变。
    • 使用场景:适合存储需要唯一性的数据,支持快速的成员检测和集合操作(如并集、交集)。
  4. 字典(Dictionary)
    • 特点:键-值对存储、无序、可变。
    • 使用场景:适合存储关联关系的数据,通过键快速访问值。
  5. 队列(Queue)
    • 特点:先进先出(FIFO)、可变。
  6. 栈(Stack)
    • 特点:后进先出(LIFO)、可变。

6. 什么是面向对象

7. 什么是鸭子类型

不关注对象类型本身,只关注是否有相对应的方法,
比如所我看到一个鸟,它走起路来想鸭子,它的叫声想鸭子,它游泳想鸭子,那么无论它本身是什么,我都可以把它当成一个鸭子

class Duck:
    def walk(self):
        print("鸭子在走路")
    def swim(self):
        print("鸭子在游泳")

class Bird:
    def walk(self):
        print("鸭子在走路")
    def swim(self):
        print("鸭子在游泳")

d = Duck()
b = Bird()
d.walk()
b.walk()
d.swim()
b.swim()

8. 常用的魔法函数有哪些

__new__:构造函数,会在创建实例的时候自动执行此函数,将此函数的返回值传入到初始化函数的self参数中
__init__:初始化函数,当对象实例出来的时候会紧接着执行初始化函数
__str__:转字符串函数,当在其他地方直接输出实例对象的时候会调用此函数,可以自定义输出的格式
__del__:析构函数,当有实例对象销毁的时候会自动执行此函数
__name__:获取但当前方法名或者类名

9. 简单说一下python中的序列化

序列化:将不能直接存储的数据变成可以存储的数据(列表,字典->str)

反序列化:将存储文件的数据拿出来恢复原样(str->列表,字典)

python中可以使用json和pickle进行序列化和反序列化

  • json是跨平台的,任何语言都能使用
    • 序列化:使用json的dumps方法进行序列化
      • json序列化时,默认遇到中文会转为unicode,如果想保留中文就在dumps方法添加一个ensure_ascii关键字参数,将他的值设置为False
    • 反序列化:使用json的loads方法进行序列化
  • pickel只能在python中使用,进行二进制的序列化,使用方法和json是一样的
  • 字符串反序列化还有一种方法是使用eval函数,eval(str)会将str转为字典进行返回

并不是所有的类型都能够被反序列化,比如集合,datetime,和一些类的实例都是不能够被反序列化的,不能被反序列化的数据会被存储到JSONEncoder这个类的default方法的参数o中,我们可以写一个类继承JSONEncoder这个类,重写其中的default方法,根据不能反序列化的类型给他转变为可序列化的类型即可。

如果将序列化后的集合和datetime模块进行反序列化,那么就需要在写一个类继承JOSNDecoder,重写其中的decode方法,根据需要反序列化的键对其进行更改

9.1 json序列化时,可以处理的数据类型有哪些?如何定制支持datetime类型

# json能支持int\float\str\bool\None\list\tuple\dict八种基本类型
# 典型的set类型,datetime类型不能被反序列化


import json
from datetime import datetime
from json import JSONEncoder, JSONDecoder

class Person:
    def __init__(self, name,age):
        self.name = name
        self.age = age

obj = {
    'k1': 10,
    'k2': 3.14,
    'k3': [],
    'k4': (1, 2), # 元组会被序列化为列表
    'k5': None,  # 这个会被序列化为null
    'k6': True,  # 这个会被序列化为true
    'k7': 'str',
    'k8': {'a', 'b'},  # 集合是不支持序列化的
    'k9': datetime.today(),  # datetime类型也是不支持序列化的
    'k10': Person("张三", 18)
}


# 默认不支持序列化的类型都会传入JSONEncoder中的default中的o形参中
# 我们只需要创建一个类,然后重写这个方法进行序列化之前的拦截即可
# 使用JSONEncode这个类
class MyJSONEncoder(JSONEncoder):
    def default(self, o):
        # 对不可序列化的类型进行拦截转换类型然后返回
        if isinstance(o, datetime):
            return o.strftime('%Y-%m-%d %H:%M:%S')
        if isinstance(o, set):
            return list(o)
        if isinstance(o, Person):
            return {'name': o.name, 'age': o.age}


str_json = json.dumps(obj, cls=MyJSONEncoder, ensure_ascii=False)
print(str_json)

# 上面那种方法将不可序列化的类型转为可序列化的类型进行序列化
# 那么反序列化时如何拿到序列化不到的类型呢
# 使用JSONDecode这个类


class MyDecoder(JSONDecoder):
    def decode(self, s):
        temp = json.loads(s)
        # 针对特殊的键,进行反序列化
        k8 = temp.pop("k8")
        temp["k8"] = set(k8)
        # print(temp["k8"],type(temp["k8"]))
        k9 = temp.pop("k9")
        temp["k9"] = datetime.strptime(k9, '%Y-%m-%d %H:%M:%S')
        k10 = temp.pop("k10")
        # print(k10)
        temp["k10"] = Person(k10['name'], k10['age'])

        return temp


obj_json = json.loads(str_json, cls=MyDecoder)
print(obj_json)

'''
小总结:
序列还就是将python数据类型转为字符串格式,方便数据进行保存
反序列化就是将字符串转为原本的数据类型
在python中有两种序列化方式,一个是json一个是pickle,
json是跨平台的,在任何语言中都能够使用
pickle只能在python中使用,pickle序列化后是看不都懂的二进制数据
这两个类都有一个方法是jumps(),这个方法就可以将数据类型转为字符串
还有一个方法是loads(),这个方法就可以将字符串转为相应的数据类型
并不是所有的类型都能够被序列化,比如列表,字符串,int,float,None,bool,元组,字典,都是可以序列化的,
但是集合,datetime, 一些类的示例都是不能够被序列化的,不能被序列化的数据会存放到JSONEncoder类的default方法的参数o中,
    我们可以写一个类去继承JSONEncoder去重写其中的default方法,根据参数o去调整不能序列化的类型然后返回,这样这个不能序列化的类型就转为了一个可以序列化的类型
如果想反序列化为原本的类型,可以继承JSONDecoder这个类,重写其中的decode方法,根据特殊类型的键去调整其本来的类型,然后将调整过后的反序列化对象进行返回

python中有一个eval()函数,传入一个字符串,它的返回类型有列表,元组,字典,这也是反序列化的一种方式,但是这个方式并不安全,极不推荐
'''

10. 深浅拷贝

在Python中,浅拷贝(ShallowCopyQ)与深拷贝(Deep Copy)主要涉及复杂对象(如列表、字典等)的复制方式,这两种复制方式处理对象内部的子对象的方式不同。
浅拷贝创建一个新对象,其内容是原对象内各元素的引用。如果原对象包含的是不可变对象(如字符串、整数等),这种区别几乎察觉不到。但如果对象包含的是可变对象(如列表、字典等),修改新对象中的可变元素将影响到原对象,因为两者引用的是同一个可变元素。Python标准库中的copy模块提供的copy函数可以用来执行浅拷贝。
深拷贝不仅复制了原对象,而且递归地复制了对象内的所有可变元素及其包含的所有元素,因此原对象和新对象完全独立。对新对象的任何修改都不会影响原对象,反之亦然。这在处理包含复杂、嵌套对象的情况时非常有用。copy模块提供的deepcopy()函数用于执行深拷贝。

浅拷贝可以使用自身的copy方法,也可使用copy模块下的copy方法。拷贝的是对象内各元素的引用,如果对象内是可变数据类型,那么更改拷贝后的对象会连同原对象一起更改

深拷贝使用的是copy模块下的deepcopy方法,拷贝的是对象内各元素的值,无论对象内是什么类型的数据,更改其中一个对另一个完全没有影响。深拷贝出来的两个对象完全独立,互不影响

11. 装饰器

在不改变原函数功能的情况下为其增加新的功能。比如给某个函数增加一个运行时间开销统计的功能就能后使用到装饰器。

装饰器就是在需要增加功能的方法名上添加一个语法糖。@+闭包名字

说到装饰器就离不开闭包,闭包的本质还是函数,只不过这个函数可以为其他函数增加新的功能

闭包需要三个要素

  1. 外部函数嵌套内部函数
  2. 外部函数将内部函数名返回
  3. 内部函数可以使用外部函数的局部变量

有这三个要素的就是一个装饰器,就可以在想增加功能的函数上添加语法糖

12. 异步与同步

  • 同步:当有多个程序运行的时候处于后面的程序需要等待前面的程序执行完毕,才能开始执行。也就是说当一个操作进行中,程序不能做其他的事情
  • 异步:程序在发起一个耗时操作(文件读写,网络请求,数据库连接)后,不会等待其完成,而是继续执行后面的操作,也就是说程序在等待耗时操作的同时可以执行其他任务,从而提高了程序的并发性和相应能力

13. 元类(metaclass)

实例是由类创建的,而类是由元类创建的,目的是创建和加工一个类

可以使用type进行创建类

# 第一个参数是类的名字,第二个参数是需要继承的父类,第三个参数是类中的内容,比如类注释,类属性,类方法
name = type("name",(),{})
# 也可以在类后的小括号添加metaclass指定哪个元类来创建类
# 这样可以拦截类的构建过程,可以对类进行加工,默认为type
class Person(metaclass=MetaClass):
    
    
# 比如拦截类的创建过程,对不规范的用户名进行拦截,并修改
# 假设不规范的命名是:XxxXxxXxx
# 更改后的命名是:xxx_xxx_xxx
class MyType(type):
    # 拦截类的创建过程
    def __new__(cls, *args, **kwargs):
        # print(args[2])
        new_dict = {}
        for k, v in args[2].items():
            # print(k, v)
            # 判断函数是不是魔法函数,是就不管它
            if not k.startswith("__"):
                new_key = ''
                for i in range(len(k)):
                    # 判断大写字母,若有,将大写字母变为小写
                    if k[i].isupper():
                        # 在原本大写字母前加下划线,第一个若第一个字母时大写,则不加
                        if i != 0:
                            new_key += '_'
                        new_key += k[i].lower()
                    else:
                        # 构造修改好的函数名
                        new_key += k[i]
                # 将原本的函数实现添加到修改后的函数名中
                new_dict[new_key] = v
            else:
                # 将魔法函数的函数实现或者本来就规范的函数名的实现还给原本的函数名
                new_dict[k] = v
        # 构造新的构造函数的第三个参数
        new_args = (args[0], args[1], new_dict)
        # 调用构造函数实现类的创建
        return super().__new__(cls, *new_args, **kwargs)

class Person(metaclass=MyType):
    def SayHello(self):
        print("hello")
    def SayHi(self):
        print("hi")

p = Person()
# p.SayHello()
p.say_hello()
p.say_hi()

14. 可迭代,迭代器,生成器的区别

  • 可迭代就是具有遍历的功能。比如str,列表,元组,字典。其类的内部实现了__iter__方法
  • 迭代器除了实现了__iter__方法之外还实现了__next__方法,__iter__方法返回迭代器自身,而__next__方法返回容器的下一个元素,如果没有元素则抛出StopIteration异常
  • 生成器是一种特殊的迭代器,通过在函数内部使用yield关键字创建,在使用yield关键字进行拆功创建后,其函数的返回值会作为异常的信息,当出现异常并打印异常信息时才会显示出来
  • 还有一种生成器时元组推导式,元组推导式返回的结果是一个生成器

15. *args和**kwargs的区别

这两种都是定义可变长参数的形式

  • *args用于接收位置参数,以元组的形式进行接收
  • **kwargs用于接收关键字参数,以字典的形式进行接收
  • 关键字参数在位置参数之后,所有*args必须在**kwar之前

16. is和==的区别

  • ==是python中的比较运算符,用来比较两个对象的值于类型是否相等

  • is判断是两个对象的id是否相同

17. 如何漫游一个文件目录,有哪两种方法

  1. 用递归找

  2. 用os.walk返回生成器,生成器每一个元素都有三个部分,第一部分是当前目录,第二部分是当前目录下的子目录,第三部分是当前目录下的文件

    # 1.使用os.walk漫游文件
    # 返回的是一个生成器,里面低第一个存放的是当前路径,第二个存放的是子目录,第三个存放的是当前目录下的文件
    import os
    
    # obj = os.walk("../pythonDemo")
    # for data in obj:
    #     print(data[0],data[1],data[2])
    
    # 2. 使用递归进行漫游
    def traverse_dir(directory):
        for item in os.listdir(directory):
            # 将遍历的文件以路径的形式进行展现
            new_path = os.path.join(directory, item)
            # print(new_path)
            if os.path.isdir(new_path):
                print(f"目录:{item}")
                traverse_dir(new_path)
            else:
                print(f"文件:{item}")
    
    
    traverse_dir("../pythonDemo")
    

18. 正则使用经验

正则:字符串匹配,搜索,替换模块

常用方法

  • findall():返回列表
  • search():返回Match或者None 获取内容使用group()
  • match():是不是以指定规则作为开头,返回Match或者None
  • fullmatch():是不是指定字符

19. IO读写

  • 使用Open获取一个文件

  • Open("filepath",读写模式,编码方式)

  • 常见的读写模式

    • r:只读
    • w:只写
    • a:追加
    • rb:读二进制文件
    • wb:写二进制

20. 进程与线程

进程与线程都是用于提升程序效率的技术(并行执行)

  • 进程:由操作系统分配资源和调度,每个进程之间都有自己的独立内存,一个进程默认有一个线程,进程的开销较大,但隔离性强,进程之间的数据默认是不共享(可以使用进程之间的Queue模块实现数据共享)

    """进程需要multiprocessing包,使用其中的Process(target='')方法用来创建进程.
    无论时进程还是线程都需要在主方法main中进行启动.
    可以使用join进行阻塞进程,阻塞是在进程或者线程开启之后才能进行"""
    
    
    # 进程之间通过queue实现数据共享
    # 生产者,消费者模式
    
    # 消费者
    def p1_main(queue, name):
        while True:
            time.sleep(3)
            print(f"{name}进行消费:{queue.get()}")
    
    
    # 生产者
    def p2_main(queue):
        while True:
            time.sleep(1)
            queue.put(random.randint(1, 100))
    
    
    def main():
        queue = Queue(maxsize=10)
        p1 = multiprocessing.Process(target=p1_main, args=(queue, 'p1'))
        p0 = multiprocessing.Process(target=p1_main, args=(queue, 'p0'))
        p3 = multiprocessing.Process(target=p1_main, args=(queue, 'p3'))
    
        p2 = multiprocessing.Process(target=p2_main, args=(queue,))
        p1.start()
        p0.start()
        p3.start()
    
        p2.start()
        p1.join()
        p0.join()
        p3.join()
        p2.join()
    
    
    if __name__ == '__main__':
        main()
    
  • 线程:是进程的一个执行单元,一个进程可以有多个线程,线程共享进程之间的资源,线程的崩溃可能会带来进程的崩溃,进程的开销小,线程之间的数据是共享的

    • 优化:线程池,预先创建一定数量的线程或者进程放入池子,使用时在池子中获取,使用后放入池子,避免反复的创建与销毁

21. Async与await异步函数

  • async定义一个异步函数,使其能够在事件循环中进行异步操作,可以通过await等待其他异步函数完成,不会阻断整个程序的执行
  • await时,python会挂起当前的异步函数,执行其他的异步任务

22. 网络编程常见的通信协议

  • http:超文本传输协议 用于web浏览器和web服务器之间传输数据的协议,它基于TCP协议
  • https:安全超文本传输协议 https在http的基础上加入了 SSL/TLS 加密,用于保护数据在客户端和服务器之间的传输安全
  • TCP:传输控制协议 是一种面向连接的,可靠的协议,它在通信双方之间建立可靠的连接,并提供数据传输的保证
  • UDP:用户数据报协议 是一种面向无连接的,不可靠的协议,它不保存数据传输的可靠性和顺序性,但具有低延迟的特点
  • FTP:文件传输协议 用于客户端和服务器之间传输文件,支持文件上传和下载操作
  • SMTP:简单邮件传输协议 用于发送电子邮件
  • pop3,IMAP:用于接收电子邮件

标签:总结,__,函数,python,对象,json,new,基础理论,序列化
From: https://www.cnblogs.com/Leybxin-AXB/p/18321016

相关文章

  • python编码规范
    本篇讲的是代码格式化的问题,解决格式化的方法在最下方,不想看内容的,滑到最下方就好了。一、变量的命名规则1.组成:字母、数字、下划线2.不可以以数字开头3.不建议使用下划线开头4.命名需见名知意5.不要与关键字重名。如何查找所有关键字?importkeywordprint(keyword.k......
  • Python爬虫开发中的常用库与框架安装指南
    在Python爬虫开发中,选择合适的库和框架可以大大提高开发效率和爬虫的性能。本文将介绍一些常用的解析库、请求库、储存库、Web库、App爬取库以及爬虫框架,并展示如何使用pip命令进行安装。一、解析库1.BeautifulSoupBeautifulSoup是一个用于从HTML或XML文件中提取数据的Pyth......
  • 如何数据防泄漏|十款热门防泄密软件推荐(帮你总结)
    “防患于未然,安不忘危。”企业数据的安全与保密不仅是企业生存和发展的基石,更是法律与道德的双重要求。如何有效防止数据泄漏? 本文将围绕这一主题,为您推荐十款热门的防泄密软件,并首先探讨企业数据保密的基本策略。第一部分:如何企业数据保密企业数据保密的核心在于构建全......
  • 如何在Python中的指定项目之后添加新项目到嵌套列表?
    给定的列表是这样的。list1=[10,20,[300,400,[5000,6000],500],30,40]预期输出是这样的。我知道这是一个非常基本的问题,但我很困惑。输出:[10,20,[300,400,[5000,6000,7000],500],30,40]我希望有人能帮助我解决这个问题。并解释了嵌套列表的插入功......
  • python带界面实现word文档比对功能
    python实现word文档比对的功能较简单,笔者这里将其界面话,可以指定输入比对的文档,相似度,最小相似参数等。输出的结果以word的形式保存,重复部分会标出,基本实现了商业软件的功能。先看界面这里不废话了,直接给出全部源码,觉得好的点个赞。程序打包的话,自己百度。fromtkinterimp......
  • 具有固定字典键的 Python 函数返回类型提示
    我有一个函数返回一个始终具有相同键的字典(通过网络发送并使用json进行“字符串化”)。基本上我的函数看起来像这样:defgetTemps(self)->dict:"""getroomandcputemperaturein°Caswellashumidityin%"""#sendtemperaturerequesttoserve......
  • 在类型提示中使用 Type[class_name] 而不是仅使用 class_name 时,python 未解析的属性
    我想输入提示继承结构,但我不知道如何正确执行。这个想法是函数c可以采用A的任何子类。一些子类具有其他子类没有的属性,并且这些属性不是在父类中定义,而是在子类中定义。函数c检查子类,如果它是正确的,则使用该类的特定属性。在此设置中,PyCharm抱怨该参数不在父类中。from......
  • python的包管理
    获取现有项目有那些依赖安装pipreqspipinstallpipreqs在项目根目录执行pipreqs.--encoding=utf8--force--pypi-server=http://mirrors.aliyun.com/pypi/simple/根据生成文件安装依赖pipinstall-rrequriements.txtpipreqs命令选项Options:--use-local......
  • 如何在 python selenium 中禁用广告隐私设置?
    我对上面有一些问题。当然,当我尝试绕过cloudflare验证码时,我的策略已经破坏了任何cloudflare。但有一些问题。当我在pythonselenium中打开新选项卡时,会弹出广告隐私窗口。谁有解决这个问题的经验。谢谢您的帮助。一旦通过,就不会再发生了。我理解你想在......
  • [附开题]flask框架的基于微信小程序的医院远程预约挂号系统设计与实现6ky98(python+源
    本系统(程序+源码+数据库+调试部署+开发环境)带论文文档1万字以上,文末可获取,系统界面在最后面。系统程序文件列表开题报告内容研究背景随着医疗需求的日益增长和互联网技术的飞速发展,传统的医院挂号方式已难以满足患者高效、便捷的就医需求。患者往往需要长时间排队等待挂号......