1.简述 OSI 7层模型及其作用?(2分)
OSI协议 | 作用 |
---|---|
应用层 | 文件传输,电子邮件,文件服务,虚拟终端 TFTP,HTTP,SNMP,FTP,SMTP,DNS,Telnet |
表示层 | 数据格式化,代码转换,数据加密 没有协议 |
会话层 | 解除或建立与别的接点的联系 没有协议 |
传输层 | 提供端对端的接口 TCP,UDP |
网络层 | 为数据包选择路由 IP RIP |
数据链路层 | 传输有地址的帧以及错误检测功能ARP |
物理层 | 以二进制数据形式在物理媒体上传输数据 |
2.简述 TCP三次握手、四次回收的流程。(3分)
三次握手:
第一次握手:建立连接时,客户端发送syn包(syn=j)到服务器,并进入SYN_SENT状态,等待服务器确认;SYN:同步序列编号(Synchronize Sequence Numbers)。
第二次握手:服务器收到syn包,必须确认客户的SYN(ack=j+1),同时自己也发送一个SYN包(syn=k),即SYN+ACK包,此时服务器进入SYN_RECV状态;
第三次握手:客户端收到服务器的SYN+ACK包,向服务器发送确认包ACK(ack=k+1),此包发送完毕,客户端和服务器进入ESTABLISHED(TCP连接成功)状态,完成三次握手。
四次挥手:
先由客户端向服务器端发送一个FIN,请求关闭数据传输。
当服务器接收到客户端的FIN时,向客户端发送一个ACK,其中ack的值等于FIN+SEQ
然后服务器向客户端发送一个FIN,告诉客户端应用程序关闭。
当客户端收到服务器端的FIN是,回复一个ACK给服务器端。其中ack的值等于FIN+SEQ
3.TCP和UDP的区别?(3分)
TCP:安全可靠,面向连接,传输速度慢,能传递的数据长度不限,提供全双工通信
UDP:无连接,不可靠,面向数据报,传输速度快,能传递的数据长度有限,支持一对一、一对多、多对一和多对多交互通信
4.什么是黏包?(2分)
当两条或多条消息发送时接收到的消息变成一条或者出现接收不准确的情况就是粘包
5.什么 B/S 和 C/S 架构?(2分)
- B/S 架构 浏览器与服务端架构,实际上是C/S架构中的一种,更节省资源 不用更新 不依赖环境
- C/S 架构 客户端与服务端架构,安全性更好,但程序比较庞大
6.请实现一个简单的socket编程(客户端和服务端可以进行收发消息)(3分)
7.简述进程、线程、协程的区别?(3分)
- 进程是计算器最小资源分配单位 .
- 线程是CPU调度的最小单位 .
- 进程切换需要的资源很最大,效率很低 .
- 线程切换需要的资源一般,效率一般(当然了在不考虑GIL的情况下) .
- 协程切换任务资源很小,效率高(协程本身并不存在,是程序员通过控制IO操作完成) .
- 多进程、多线程根据cpu核数不一样可能是并行的,但是协程是在一个线程中 所以是并发
8.什么是GIL锁?(2分)
全局解释器锁 CPython在执行多线程的时候并不是线程安全的,所以为了程序的稳定性,加一把全局解释锁,能够确保任何时候都只有一个Python线程执行。
9.进程之间如何进行通信?(2分)
- Queue
- Pipe
10.Python如何使用线程池、进程池?(2分)
- 引入进程池与线程池
- 使用ProcessPoolExecutor进程池,使用ThreadPoolExecutor线程池
11.请通过yield关键字实现一个协程? (2分)
def consumer():
r = ''
while True:
n = yield r #执行的中断点
if not n:
return
print('[消费者] 正在消费:{0}'.format(n))
r = '200 人民币'
def produce(c):
c.send(None) #启动消费者(生成器)——实际上是函数调用,只不过生成器不是直接象函数那般调用的
n = 0
while n < 5:
n = n + 1
print('[生产者] 正在生产:{0}'.format(n))
r = c.send(n) #给消费者传入值——实际上也是函数调用
print('[生产者] 消费者返回:{0}'.format(r))
c.close()
c = consumer()#构造一个生成器
produce(c)
12.什么是异步非阻塞? (2分)
- 程序执行时,A调用B,不用等待B返回结果,而是去做其他事情,等B有结果时通知A
13.什么是死锁?如何避免?(2分)
- 线程死锁是指由于两个或者多个线程互相持有对方所需要的资源,导致这些线程处于等待状态,无法前往执行。
14.程序从flag a执行到falg b的时间大致是多少秒?(2分)
import threading
import time
def _wait():
time.sleep(60)
# flag a
t = threading.Thread(target=_wait)
t.setDeamon(False)
t.start()
# flag b
结果:60s
15.程序从flag a执行到falg b的时间大致是多少秒?(2分)
import threading
import time
def _wait():
time.sleep(60)
# flag a
t = threading.Thread(target=_wait)
t.setDeamon(True)
t.start()
# flag b
0.01s
16.程序从flag a执行到falg b的时间大致是多少秒?(2分)
import threading
import time
def _wait():
time.sleep(60)
# flag a
t = threading.Thread(target=_wait)
t.start()
t.join()
# flag b
60s
17.读程序,请确认执行到最后number是否一定为0(2分)
import threading
loop = int(1E7)
def _add(loop:int = 1):
global number
for _ in range(loop):
number += 1
def _sub(loop:int = 1):
global number
for _ in range(loop):
number -= 1
number = 0
ta = threading.Thread(target=_add,args=(loop,))
ts = threading.Thread(target=_sub,args=(loop,))
ta.start()
ta.join()
ts.start()
ts.join()
不一定
18.读程序,请确认执行到最后number是否一定为0(2分)
import threading
loop = int(1E7)
def _add(loop:int = 1):
global number
for _ in range(loop):
number += 1
def _sub(loop:int = 1):
global number
for _ in range(loop):
number -= 1
number = 0
ta = threading.Thread(target=_add,args=(loop,))
ts = threading.Thread(target=_sub,args=(loop,))
ta.start()
ts.start()
ta.join()
ts.join()
一定为0
19.MySQL常见数据库引擎及区别?(3分)
20.简述事务及其特性? (3分)
- 事务是用户定义的数据库操作序列,这些操作要么都成功,要么都失败,不可分割,
- 原子性,所有操作要么都做。要么都不做
- 一致性,是数据控从一个一致状态变成另一个一致状态
- 持续性,事务一旦提交,对数据库的改变是永久的
- 隔离性,一个事务内部的操作及使用的数据对并发的其他事务是隔离的
21.事务的隔离级别?(2分)
- 读未提交
- 读提交
- 可重复读取
- 可序列化
22.char和varchar的区别?(2分)
char是定长类型:最多存放255个字符
varchar是可变类型:最大长度为65535个字节,varchar可存放的字符数跟编码有关
23.mysql中varchar与char的区别以及varchar(50)中的50代表的含义。(2分)
char是定长类型:最多存放255个字符
varchar是可变类型:最大长度为65535个字节,varchar可存放的字符数跟编码有关
varchar(50)代表可以存放50个字节
24.MySQL中delete和truncate的区别?(2分)
delete和truncate都是删除表数据,但是trancate是删除整个表的数据