python开发之面试题

python基础面试题

1、对字典操作和深浅拷贝的理解

def func(m):
    for k,v in m.items():
        m[k+2] = v + 2 #这样做是会报错的,RuntimeError: dictionary changed size during iteration

m = {1:2,3:4}
l = m
l[9]=10
# func(l) #
m[7]=8

# 1、在python中遍历字典的时候是不能对字典涉及的键进行操作(键的添加和删除)
# 2、深浅拷贝
print(l) # 注释掉函数后的结果是 {1: 2, 3: 4, 9: 10, 7: 8}
print(m) #                      {1: 2, 3: 4, 9: 10, 7: 8}
from copy import deepcopy
m = {1:2,3:4}
l = m # 浅拷贝
l2 = deepcopy(m) # 深拷贝
l[9]=10
m[7]=8

print(l) # 注释掉函数后的结果是 {1: 2, 3: 4, 9: 10, 7: 8}
print(m) #                      {1: 2, 3: 4, 9: 10, 7: 8}
print(l2) #{1: 2, 3: 4}

 2、字符串格式化:%和format有什么区别

'''
1、python新版本推荐使用format
2、python2.6才加入的支持format语法支持
3、python3.6引入了新特性f-string
'''
name = 'Fred'
res = f"he said his name is {name}"
print(res) #he said his name is Fred

3、可变对象不建议做关键字参数

def foo(arg,li=[]): 
    li.append(arg)
    return li

list1 = foo(21)
list2 = foo(21,[1,])
list3 = foo(28)

print(list1) #[21,28]
print(list2) #[1,21]
print(list3) #[21.28]

4、列表切片

li = [11,22,33,44]
print(li[10:]) #[]

5、fib 斐波那契

# 1
fib = lambda n:n if n<2 else fib(n-1) + fib(n-2)
print(fib(6))
# 2
def fib(n):
    a,b = 0,1
    for _ in range(n):
        a,b = b, a+b
    return b

6、去重

# set集合
l1 = ['b','c','d','b','a','c','c']
print(set(l1))

# 用字典
l2 = {}.fromkeys(l1).keys()
print(l2)

#列表推导式
l3 = []
[l3.append(i) for i in l1 if i not in l3]
print(l3)
for i in l1:
    if i not in l3:
        l3.append(i)
print(l3)

7、合并两个有序列表

def loop_merge_sort(l1,l2):
    tmp = []
    while len(l1)>0 and len(l2)>0:
        if l1[0]<l2[0]:
            tmp.append(l1[0])
            del l1[0]
        else:
            tmp.append(l2[0])
            del l2[0]
    tmp.extend(l1)
    tmp.extend(l2)
    return tmp

print(loop_merge_sort([1,3,5],[1,2,7]))

8、单例模式:在__new__方法上把类实例绑定到类变量_instance上,如果cls._instance为None表示还没有实例化过实例化该类并返回,如果cls._instance不为None表示该类已经实例化,直接返回cls._instance

class SingleTon(object):
    def __new__(cls, *args, **kwargs):
        if not hasattr(cls,'_instance'):
            cls._instance = object.__new__(cls,*args,**kwargs)
        return cls._instance

class TestSingle(SingleTon):
    a = 1

t1 = TestSingle()
t2 = TestSingle()
print(id(t1),'--',id(t2))

9、读li进行计数,返回出现次数最多的

l1 = ['a','b','c','d','a','v','s','d','c','a','c','c']
# 法1
from collections import Counter
result = Counter(l1).most_common(1)
print(result)

# 法2
def all_list(l1):
    """获取所有元素的出现次数,使用list中的count方法"""
    result = {}
    for i in set(l1):
        result[i] = l1.count(i)
    return result

result = all_list(l1)
for k,v in result.items():
    if result[k] == max(result.values()):
        print(k,v)

10、上下文实现原理

'''
上下文管理协议,即with语句,为了让一个对象兼容with语句,必须在这个对象的类中声明__enter__和__exit__方法
作用:
1.使用with语句的目的就是把代码块放入with中执行,with结束后,自动完成清理工作,无须手动干预
2.在需要管理一些资源比如文件,网络连接和锁的编程环境中,可以在__exit__中定制自动释放资源的机制,
  你无须再去关系这个问题,这将大有用处
'''
class Open:
    def __init__(self,filepath,mode="r",encode="utf-8"):
        self.f = open(filepath,mode=mode,encoding=encode)

    def write(self):
        pass

    def __getattr__(self, item):
        return getattr(self.f,item)

    def __del__(self):
        print("--->del")
        self.f.close()

    def __enter__(self):
        print("出现with语句,对象会调用我")
        return self

    def __exit__(self, exc_type, exc_val, exc_tb):
        print("with结束之后,会执行我啦")

with Open('1.txt') as f:
    f.write()
'''
出现with语句,对象会调用我
with结束之后,会执行我啦
--->del
'''

socket问题

1、为什么会出现粘包?

首先只有在TCP协议中才能出现粘包现象,这是因为TCP协议是面向流的协议,
在发送数据的数据传输过程中还有缓存机制来避免数据丢失,因此在连续发送
小数据的时候以及接受大小不符的时候都容易出现粘包现象,本质还是因为我们在接受数据的时候
不知道发送的数据的长度。

 2、如何解决粘包?

在传输大量数据之前先告诉接收端要发送的数据的大小。如果要想更好的解决问题,可以采用struct
模块来定制协议。

3、GIL锁?

1、GIL导致了同一时刻只能有一个线程访问CPU。
2、锁的是什么?锁的是线程
3、GIL是python语言的问题吗?不是,是CPython解释器的特性。

4、线程的概念?

进程是最小的内存分配单元,线程是操作系统调度的最小单位,线程直接被CPU执行,进程内至少含有一个线程
也可以开启多个线程。
特点:
    开启一个线程所需要的时间要远小于开启一个进程,
    多个线程内部有自己的数据栈,数据不共享
    全局变量在多个线程之间是共享的。
原文地址:https://www.cnblogs.com/crazyforever/p/9074100.html