python进阶题_Python进阶题

本文探讨了Python进阶问题,包括如何获取列表中第二大的值、Python内存管理机制、垃圾回收机制的原理,以及用两个队列实现栈的方法。此外,还介绍了链表的数据结构及其逆转实现,通过具体的代码实例加深理解。
摘要由CSDN通过智能技术生成

1、如何获取列表中第二大的值?

#先去重,在排序,取值

lst = [1,2,3,4,5,5,5,5,5,5,5,5]

setvar = set(lst)

# 列表.sort 类型有局限性,只能是列表,基于原有列表进行修改

# sorted 容器类型数据皆可以,返回新列表

lst = sorted(setvar)

print(lst) # [1, 2, 3, 4, 5]

res = lst[-2]

print(res)

2、简述Python内存管理机制。

# 一.计数器

#特点:引用技术如果是0,把这个值从内存中释放掉

a = 100

b = a

print(b)

del b

a = 100 (100这个值计数为1,被引用过1次)

b = a (100这个值计数为2,被引用过2次)

del b (100这个值计数为1,被引用过1次,100本身不会被删掉)

del a (100这个值计数为0,被引用过0次,100本身被删掉)

#缺点:在维护引用计数时,又可能数据产生循环引用,造成数据不能删除,造成内存泄漏

lst1 = [1,2]

lst2 = [5,6]

lst1.append(lst2)

lst2.append(lst1)

del lst1

print(lst1)

print(lst2)

3、简述Python的垃圾回收机制。

计数器,垃圾回收,内存池

# 一.计数器

特点:引用技术如果是0,把这个值从内存中释放掉

a = 100

b = a

print(b)

del b

缺点:在维护引用计数时,又可能数据产生循环引用,造成数据不能删除,造成内存泄漏

lst1 = [1,2]

lst2 = [5,6]

lst1.append(lst2)

lst2.append(lst1)

del lst1

print(lst1)

print(lst2)

# 二.垃圾回收:引用计数为主,标记清除和分带回收为辅

标记清除 : 检测标记该对象,避免出现循环引用不能删除的现象

分带回收 :

把内存中的数据分成三个区域: 新生代0,老年代1,永久代2

新生代0数据超过700 , 或者老年代1,永久代2数据超过10,自动触发内存中的垃圾回收机制

新生代0触发将清除所有三代的区域

老年代1触发会清理1,2代

永久代2触发只会清理自己

# 三.内存池

# 在同一个文件当中 (python3.6)

# -->Number 部分

1.对于整型而言,-5~正无穷范围内的相同值 id一致

2.对于浮点数而言,非负数范围内的相同值 id一致

3.布尔值而言,值相同情况下,id一致

4.复数在 实数+虚数 这样的结构中永不相同(只有虚数的情况例外)

# -->容器类型部分

5.字符串 和 空元组 相同的情况下,地址相同

6.列表,元组,字典,集合无论什么情况 id标识都不同 [空元组例外]

# 在不同的文件当中

小数据池 ; 比如整型默认开辟 -5~256 这么多数据提前在内存中驻留

4、请用两个队列来实现一个栈。

"""

栈: 先进后出,后进先出

队列: 先进先出,后进后出

"""

from queue import Queue

class Stack():

def __init__(self):

self.master_queue = Queue()

self.minor_queue = Queue()

# 入栈

def push(self,val):

self.master_queue.put(val)

# 出栈

def pop(self):

# qsize() 队列长度为0等于没数据返回None

if self.master_queue.qsize() == 0:

return None

while True:

if self.master_queue.qsize() == 1:

# 拿出队列里面最后一个元素

value = self.master_queue.get()

break

# 把临时获取的值存在辅队列里

self.minor_queue.put(self.master_queue.get())

# 重置主队列,把辅队列临时存储的值放回去

self.master_queue, self.minor_queue = self.minor_queue , self.master_queue

return value

obj = Stack()

# push 添加数据

obj.push(1)

obj.push(2)

obj.push(3)

# pop 获取数据 3 2 1

print(obj.pop())

print(obj.pop())

print(obj.pop())

print(obj.pop())

5、请用Python实现一个链表。

class Node():

def __init__(self,value,next):

self.value = value

self.next = next

head = Node("头",None)

last = head

for i in range(5):

# 创建节点对象n0 n1 n2 n3 n4

node = Node( "n%s" % (i) , None)

# 把当前创建的节点塞到上一个节点的next属性中

last.next = node

# 向下一个节点移动

last = node

# 查看链表关系

print(head.value)

print(head.next.value)

print(head.next.next.value)

print(head.next.next.next.value)

print(head.next.next.next.next.value)

print(head.next.next.next.next.next.value)

print(head.next.next.next.next.next.next)

>>>

n0

n1

n2

n3

n4

None

6、请用Python实现链表的逆转。

# ### (1) 创建链表

class Node():

def __init__(self, value, next):

self.value = value

self.next = next

head = Node("头", None)

last = head

for i in range(5): # v0 v1 v2 v3 v4

node = Node("v%s" % i, None)

last.next = node

last = node

# 查看链表的关系

print(head.value)

print(head.next.value)

print(head.next.next.value)

print(head.next.next.next.value)

print(head.next.next.next.next.value)

print(head.next.next.next.next.next.value)

print("<========>")

# 2.链表的逆转

def reverse_link_list(head):

# 要是空的,或者None,直接返回head

if not head or not head.next:

return head

# 获取上一个节点对象

prev_node = None

# 获取下一个节点对象

next_node = head.next

# 获取当前节点对象

current_node = head

while True:

# 修改next,所指向的对象

current_node.next = prev_node

# 如果下一个阶段对象是None

if not next_node: # not None

break

# 重新获取上一个对象,即把当前丢向单独存一份,以准备第二次循环时插进next属性中

prev_node = current_node

# 重新获取当前对象 , 即把下一个对象单独存储起来(下个)

current_node = next_node

# 重新获取下一个对象,即把下一个对象单独存储起来,所指向的下个新对象赋值给next_node(下下个)

next_node = current_node.next

return current_node

head = reverse_link_list(head)

print(head.value)

print(head.next.value)

print(head.next.next.value)

print(head.next.next.next.value)

print(head.next.next.next.next.value)

print(head.next.next.next.next.next.value)

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值