1.python 的数据类型(可变和不可变)
1).可变数据类型:
列表 list
字典 dict
集合 set
2).不可变类型:
整型 int
字符串 str
浮点型 float
元组 tuple
数值类型 如:复数 complex
布尔类型 bool
2.python 的去重排序
1).去重 set:
numbers = [1, 2, 2, 3, 4, 4, 5]
unique_numbers = list(set(numbers))
print(unique_numbers)
2).排序 Sorting:
sorted():
sorted()函数可以对任何可迭代对象进行排序,返回一个新的排序后的列表,原列表保持不变。
numbers = [5, 9, 1, 4, 3]
sorted_numbers = sorted(numbers)
print(sorted_numbers)
使用列表的.sort()方法:
与sorted()不同,列表的.sort()方法直接在原列表上进行排序,不返回新的列表。
numbers = [5, 9, 1, 4, 3]
numbers.sort()
print(numbers)
3.python的内存管理
1)自动垃圾回收:
Python 解释器会追踪对象的引用计数,一个对象的引用计数变为0时,说明没有任何变量指向该对象,解释器就会回收这块内存。
2)引用计数:
Python 内部为每个对象维护一个引用计数,表示有多少个变量或数据结构引用了这个对象。当对象被创建时,其引用计数初始化为1;当对象被一个新的变量引用时,引用计数增加;当变量不再引用该对象或被重新赋值时,引用计数减少。当引用计数减到0时,对象就可以被销毁并回收其占用的内存。
3)循环引用收集:
仅依赖引用计数机制有时无法处理循环引用的问题,即两个或多个对象互相引用形成一个闭环,但这些对象实际上已经不再被程序其他部分使用。为解决这个问题,Python 引入了周期检测机制,周期性地检查并打破这些循环引用,从而能够回收这些对象占用的内存。
4)分代垃圾回收:
Python 的垃圾回收机制将对象分为不同的“代”。新创建的对象归入年轻代,如果经历过一定次数的垃圾回收后仍然存活的对象会被移动到老年代。老年代的对象不常进行回收,因为它们更可能是长时间存活的对象。这种策略基于观察到的大多数对象很快变得不可达的规律,减少了垃圾回收的开销。
5) 内存池:
为了减少对操作系统分配和释放小块内存的调用(这通常比较耗时),Python 使用内存池技术预先向操作系统申请一大块内存,并在此基础上进行小块内存的分配和回收,提高了内存分配的效率。
4.python 线程与进程
1) 线程:
线程是进程内的执行单元,是CPU调度的基本单位。同一进程内的多个线程共享该进程的内存空间和资源,但每个线程有自己的程序计数器、堆栈和局部变量。
优势:
轻量级:相比进程,线程的创建和切换开销较小。
通信简便:因为共享同一地址空间,线程间可以直接访问同一进程内的数据,通信更为直接快速。
劣势:
资源共享问题:多个线程访问共享资源可能导致数据不一致,需要使用锁、信号量等同步机制来避免竞态条件。
可靠性:一个线程崩溃可能会影响到同一进程内的其他线程。
2) 进程:
进程是操作系统资源分配的基本单位,每个进程都有独立的内存空间、代码段、数据段、堆栈等,因此,进程之间的数据是隔离的。创建和切换进程的开销比较大,因为涉及到操作系统级别的资源分配。
优势:
独立性:进程之间相互独立,一个进程崩溃不会影响其他进程。
资源隔离:每个进程有自己独立的资源,适合运行大量且长时间运行的任务。
劣势:
开销大:创建和销毁进程,以及进程间的通信成本较高。
通信复杂:由于进程间地址空间隔离,进程间通信相对复杂,常用管道、套接字、共享内存等机制。
3) 选择原则:
如果你的任务需要大量的计算或者需要独立的内存空间,且任务之间关联不大,可以考虑使用多进程。
如果你的任务主要是I/O密集型(如网络请求、文件读写),或者需要频繁的数据交换,使用多线程可能会更高效。
对于CPU密集型任务且需要利用多核处理器,可以结合使用多进程和线程,根据具体场景选择合适的并发模型。
在 Python 中,可以通过multiprocessing模块来创建和管理进程,通过threading模块来创建和管理线程。
5.逻辑运算符的优先级:
() > not > and > or
6.python常用的模块:
1) os提供了许多与操作系统交互的函数,如文件操作、进程管理等。
2) sys:提供访问和使用 Python 解释器的一些功能,比如命令行参数、退出程序等。
3) math:包含数学相关的函数,如平方根、对数、三角函数等。
4) datetime:处理日期和时间,包括日期/时间的运算和格式化。
5) json:用于编码和解码 JSON 数据,方便与 Web 服务交互。
6) re:正则表达式模块,用于文本模式匹配和替换。
7) requests:一个非常流行的第三方库,用于发送 HTTP 请求,非常适合网络爬虫和API调用。
8) BeautifulSoup 和 lxml:这两个库常用于网页解析,提取 HTML 或 XML 页面中的数据。
9) pandas:数据分析领域的明星库,提供了高效的数据结构DataFrame,以及数据分析工具。
10) numpy:基础科学计算包,提供了高性能的多维数组对象和数学函数。
11) matplotlib 和 seaborn:用于数据可视化,创建静态、动态、交互式的图表。
12) flask 和 django:两个非常流行的Web框架,用于快速开发web应用。
13) sqlalchemy:SQL工具包和ORM系统,用于数据库操作。
14) unittest:Python标准库中的单元测试框架,用于编写测试用例。
15) logging:日志记录模块,帮助开发者记录程序运行过程中的信息。
-
python程序会内存溢出吗?
Python 程序确实有可能发生内存溢出。内存溢出指的是程序运行过程中消耗的内存超过了系统分配给它的可用内存空间,导致程序无法正常运行或崩溃。
Python 自带的内存管理机制,如自动垃圾回收和引用计数等,通常能有效避免一些常见的内存泄漏问题,但这并不意味着程序完全不受内存限制。以下几种情况可能导致 Python 程序出现内存溢出:1)无限增长的数据结构:
如果程序中存在不断增长的数据结构(如列表、字典等),并且增长速度超过了垃圾回收机制处理的速度,最终可能会耗尽内存。
2)循环引用:
虽然 Python 的垃圾回收器能够处理大多数循环引用问题,但在某些复杂情况下,尤其是涉及大量对象的循环引用,也可能导致内存泄露,进而引发内存溢出。
3)大文件处理不当:
一次性读取非常大的文件到内存中,或者不当的文件处理逻辑,都可能导致内存使用激增。4)第三方库的内存泄漏:
使用第三方库时,如果库内部存在内存泄漏问题,也可能导致程序内存使用持续增长。5)系统资源限制:
操作系统对每个进程可使用的内存大小有限制。即使Python程序理论上还有足够的内存可供使用,但如果超过了操作系统的限制,也会触发内存溢出错误。
采取措施:
memory_profiler
、tracemalloc
等工具分析内存使用情况,定位内存消耗高的部分。
优化数据结构和算法,避免不必要的内存占用。
分批处理大数据,避免一次性加载过多数据到内存中。
使用生成器 (generator
) 来处理大文件或大量数据流。
对于极端情况,可能需要考虑使用分布式计算框架来分散处理任务,减轻单机内存压力。
8.python装饰器:
python装饰器是一种非常有用的功能,它允许用户在不修改原始函数的情况下,给函数添加额外的功能。
装饰器本身是一个接收函数作为参数的可调用对象并返回一个新的函数,这个新函数通常会在执行原始函数之前或之后增加一些额外的操作。
基本语法:
装饰器的定义通常使用`@decorator_name`语法糖,放在函数定义之前。下面是一个简单的装饰器示例,该装饰器用于打印函数被调用的信息:
def my_decorator(func):
def wrapper():
print(f"{func.__name__} is being called")
func()
return wrapper
@my_decorator
def say_hello():
print("Hello!")
say_hello()
9.python中local对像和Threading.local对象的区别
在Python中,`local`对象并没有直接作为官方术语使用,但我们可以将其理解为一般意义上的局部变量,即在一个函数、方法、类定义或lambda表达式内部声明的变量,其作用域仅限于该定义内部。局部变量对于函数外部是不可见的,且不同函数调用之间的局部变量互不影响,不提供跨函数或跨线程的数据共享。
而`threading.local`对象是Python标准库`threading`模块中提供的一个特殊类型,用于创建线程本地存储。它允许每个线程拥有该对象属性的独立副本,从而实现了线程间数据的隔离。这意味着,即使多个线程访问同一个`threading.local`实例的属性,每个线程看到和修改的都是该属性的一个线程特有的版本,不会发生数据冲突。
总结两者之间的区别:
1) 作用域:
`local`(局部变量):作用域局限于定义它们的函数、方法、类或lambda表达式内部,是代码执行的基本范围限制。
`threading.local`对象:作用于整个线程生命周期,跨越函数调用,为每个线程提供独立的数据视图。
2) 数据共享与隔离:
`local`(局部变量):天然隔离,每个函数调用或代码块执行都有自己的独立副本,不涉及跨线程数据共享。
`threading.local`对象:提供了线程间的数据隔离机制,即使在全局范围内使用,也能确保每个线程只能访问到自己的数据副本,非常适合存储线程特有的状态信息。
3) 应用场景:
`local`(局部变量):用于控制变量的可见性和生命周期,是最基本的变量作用域概念。
`threading.local`对象:适用于多线程编程中需要维护线程特有数据的场景,如数据库连接、会话信息或线程局部缓存等。
10.Lambda函数
lambda函数是Python中一种简洁的、快速定义单行、小型匿名函数的方法。“匿名”意味着它没有具体名称,这与常规的有名的函数不同。lambda函数常用于需要短暂使用的简单功能场合,尤其是高阶函数(如`map()`、`filter()`、`sorted()`等)的参数中,或者作为字典的值等场景。
Lambda函数基本语法如下:
lambda arguments: expression
`lambda` 是关键字,用来声明这是一个lambda函数。
`arguments` 是传入lambda函数的参数列表,可以有一个或多个参数,参数之间用逗号分隔,且无需指定参数类型。
`expression` 是一个表达式,计算后作为lambda函数的返回值。注意,lambda函数只能包含一个表达式,不能包含复杂的语句或赋值操作。
double = lambda x: x * 2
print(double(5)) # 输出10
sum = lambda x, y: x + y
print(sum(3, 4)) # 输出7
sort_by_second_element = sorted([(1, 'b'), (2, 'a'), (3, 'c')], key=lambda x: x[1])
print(sort_by_second_element) # 输出[(2, 'a'), (1, 'b'), (3, 'c')]
11.python迭代器
1)
在Python中,迭代器(Iterator)是一种特殊类型的对象,它能够遍历集合中 的元素,如列表、元组、字典、集合等。迭代器的主要优点是它允许你以一种统一的方式处理不同类型的可迭代对象,并且只在需要时加载元素,这在处理大量数据时非常有用,可以节省内存。
2)基本概念:
1. 可迭代对象(Iterable):任何可以直接作用于for
循环的数据类型都是可迭代对象。比如,列表、字符串、元组、字典、集合等。
2. 迭代器(Iterator):从可迭代对象中创建的,可以记住遍历的位置,迭代器对象实现了__iter__()
和__next__()
两个方法。__iter__()
返回迭代器本身,__next__()
返回容器的下一个项目,当没有更多项目时,引发StopIteration
异常。
3)创建迭代器:
你可以使用iter()
函数从一个可迭代对象创建一个迭代器:
```python
my_list = [1, 2, 3]
my_iterator = iter(my_list)
```
4)使用迭代器
一旦创建了迭代器,就可以通过`next()`函数或在`for`循环中使用它来遍历元素:
```python
# 使用next()函数手动迭代
print(next(my_iterator)) # 输出: 1
print(next(my_iterator)) # 输出: 2
# 或者在for循环中自动迭代
for item in my_iterator:
print(item) # 输出剩余的元素
```
标签:Python,函数,迭代,python,笔记,面试,对象,内存,线程
From: https://www.cnblogs.com/ckh2023/p/18237768