day8--socketserver作业
fileno()文件描述符
handle_request()处理单个请求
server_forever(poll_interval=0.5)处理多个请求,poll_interval每0.5秒检测是否关闭,
作业:开发一个支持多用户在线的FTP程序
要求:
1.用户加密认证;
2.允许同时多用户登录;
3.每个用户有自己的家目录,且只能访问自己的家目录;
4.对用户进行磁盘配额,每个用户的可用空间不同;
5.允许用户在ftp.server上随意切换目录;
6.允许用户查看当前目录下文件;
7.允许上传和下载文件,保证文件一致性;
8.文件传输过程中显示进度条;
9.附加功能,支持文件的断点续传。
发送文件的大致思路:
接收文件的大致思路:
遍历空的文件,如果一个文件是空的,Python是不会执行后面缩进的代码的,空的文件。
http://www.cnblogs.com/liujiacai/p/7417953.html
http://www.cnblogs.com/lianzhilei/p/5869205.html
http://www.bubuko.com/infodetail-1758633.html
由于不是做运维的,对一些系统的操作不是很熟悉,因此首先完成了文件的上传与下载:下面来看看这两个功能:
客户端:
import socket,os,json,sys class Myclient(object):
'''定义客户端'''
def __init__(self):
'''定义socket()实例'''
self.client = socket.socket() #生成soket()实例 def connect(self,ip,port):
"""定义连接"""
self.client.connect((ip,port)) def interactive(self):
'''定义和用户交互'''
while True:
cmd = input("请输入指令>>:").strip() #用户输入指令
if len(cmd) == :
print("指令不能为空!!!")
continue #指令不能为空
cmd_str = cmd.split()[] #指令由两种形式
if hasattr(self,cmd_str): #判断指令是否存在
func = getattr(self,cmd_str) #指令存在,则获取对应的方法
func(cmd)
elif cmd_str == 'q':
break
else:
self.help()
continue def help(self):
msg = """
ls
pwd
cd
put filename
get filename
"""
print("指令名称",msg) def put(self,cmd):
'''定义上传数据接口'''
cmd_list = cmd.split()
if len(cmd_list) > :
'''指令是由指令名和文件名构成'''
filename = cmd_list[] #获取文件名
if os.path.isfile(filename): #检测上传的文件名是否存在
'''文件名存在,则要告诉服务器端上传的文件名,文件大小,并检测服务器是否有相应的方法'''
filesize = os.stat(filename).st_size
msg_dic = {
"action":"put",
"filename":filename,
"filesize":filesize
}
'''转换为字节码的形式进行传输'''
self.client.send(json.dumps(msg_dic).encode("utf-8")) #转换为json格式进行上传,便于服务器接收后处理
server_response = self.client.recv() #等待服务器传回信息,防止粘包
self.client.send("收到了".encode("utf-8"))
if int(server_response.decode("utf-8")):
'''根据客户端反馈,服务器端是否存在相同的文件名'''
file_exist = int(self.client.recv().decode("utf-8"))
if file_exist:
'''服务器端存在相应的文件'''
while True:
cover_flag = input("文件已存在,是否覆盖原文件(y/n):")
if cover_flag == "y":
self.client.send("y".encode("utf-8"))
break
elif cover_flag == "n":
new_filename = input("请输入新的文件名>>:")
self.client.send(("n "+new_filename).encode("utf-8"))
break
else:
print("您输入的指令有误,请重新输入!!!")
continue
else:
self.client.send("新创建".encode("utf-8")) '''上面准备工作完毕,开始传输文件'''
with open(filename,'rb') as f:
for line in f:
self.client.send(line) #发送数据
'''客户端等待服务器端传来消息,告知上传成功'''
response = self.client.recv()
print(response.decode("utf-8")) #数据是否上传成功,告知用户
else:
print("服务器端不存在相应的指令!!!") else:
print("要上传的文件名不存在!") else:
print("没有输入要上传的文件名!!!") def get(self,cmd):
'''从服务器端下载数据'''
cmd_list = cmd.split() #获取用户输入指令
if len(cmd_list) > : #是由指令和文件名构成
filename = cmd_list[]
msg_dic = {
"filename":filename,
"action":"get"
} #把指令封装成字典发送给服务器
self.client.send(json.dumps(msg_dic).encode("utf-8")) #把指令以json形式传给服务器
server_response = int(self.client.recv().decode("utf-8")) #接收服务端发挥的指令,判断是否支持此方法
self.client.send("收到指令!".encode("utf-8"))
if server_response:
file_exists = int(self.client.recv().decode("utf-8")) #下载文件存在与否标识符
self.client.send("收到标识符".encode("utf-8")) #告知服务器收到标识符,防止粘包
if file_exists:
'''文件存在,则准备接收数据,会接收服务器发送过来的文件大小'''
file_mess = json.loads(self.client.recv().decode("utf-8"))
self.client.send("文件信息接收成功,开始进行文件接收!".encode("utf-8"))
filesize = file_mess["filesize"]
while True:
'''确定文件名'''
if os.path.isfile(filename):
'''说明客户端存在文件,就要让用户选择是否覆盖'''
choice_cover = input("文件名重复,是否覆盖现有文件(y/n)>>:")
if choice_cover == "y":
filename = filename
break #覆盖文件之后退出循环
elif choice_cover == "n":
filename = input("请输入新的文件名>>:")
'''由于用户输入了新的用户名,我们不知道此文件是否重名,因此重新检测一下,确保不重名'''
continue
else:
filename = filename
break #得到文件名之后退出循环
recvive_size =
with open(filename,'wb') as file:
while recvive_size < filesize:
data = self.client.recv()
file.write(data)
recvive_size += len(data)
print("数据下载完成!!!")
self.client.send("接收完毕".encode("utf-8"))
else:
print("要下载的文件不存在!!!") else:
print("服务器不支持此功能!!!") else:
print("对不起,输入有误!")
self.help() if __name__ == "__main__":
try:
client = Myclient()
client.connect("localhost",)
client.interactive()
except KeyboardInterrupt as e:
print("客户端断开!!!",e)
上面客户端只实现了上传和下载功能,没有实现其他系统操作有关的功能,后续将逐步完善;
服务器端:
'''定义服务器端'''
import socketserver,json,os class MyTcpServer(socketserver.BaseRequestHandler):
'''定义服务器端,socketserver,继承的是BaseRequestHandler类'''
def handle(self):
'''服务器端所有的功能都在handle()里面进行处理,因此接收数据也是在handle()中,只是处理的时候,调用下面模块而已'''
while True:
data = self.request.recv()
if len(data) == :
print("客户端断开")
break
msg_dic = json.loads(data.decode("utf-8")) #服务器端接收指令
cmd = msg_dic["action"]
if hasattr(self,cmd): #判断服务器是否有相应的指令
self.request.send("".encode("utf-8"))
self.request.recv()
func = getattr(self,cmd)
func(msg_dic)
else:
self.request.send("".encode("utf-8"))
self.request.recv() def put(self,msg_dic):
'''定义上传的服务器代码'''
filename = msg_dic['filename']
filesize = msg_dic["filesize"]
'''判断服务器端是否存在对应的文件名'''
recvive_size =
if os.path.isfile(filename):
'''如果服务器存在相应的文件名,则询问客户端是否覆盖'''
self.request.send("".encode("utf-8")) #文件存在,循环客户端是否覆盖
response = self.request.recv().decode("utf-8")
response = response.split()
'''如果用户让覆盖则覆盖,否则重新创建''' if response[] == "y":
'''覆盖'''
with open(filename,"wb") as f1:
while recvive_size < filesize:
data = self.request.recv()
f1.write(data)
recvive_size += len(data)
self.request.send("文件接收成功!".encode("utf-8")) else:
'''不覆盖,新创建'''
new_filename = response[]
with open(new_filename,'wb') as f:
while recvive_size < filesize:
data1 = self.request.recv()
f.write(data1)
recvive_size += len(data1)
self.request.send("文件接收成功!".encode("utf-8")) else:
'''如果服务器不存在相应文件名,则创建'''
self.request.send("".encode("utf-8"))
self.request.recv()
with open(filename,'wb') as f2:
while recvive_size < filesize:
data1 = self.request.recv()
f2.write(data1)
recvive_size += len(data1)
self.request.send("文件接收成功!".encode("utf-8")) def get(self,msg_dict):
'''基础交流结束,服务器支持文件下载功能,开始文件下载操作'''
filename = msg_dict["filename"]
if os.path.isfile(filename):
self.request.send("".encode("utf-8")) #文件存在告知客户端
self.request.recv()
filesize = os.stat(filename).st_size
'''首先告知客户端文件大小,让这边做好接收准备'''
file_mess = {
"filesize":filesize,
}
self.request.send(json.dumps(file_mess).encode("utf-8")) #以json格式发送给客户端
self.request.recv() #防止粘包,客户端回应服务器接收完毕
with open(filename,"rb") as f_obj:
for line in f_obj:
self.request.send(line)
self.request.recv() else:
self.request.send("".encode("utf-8")) #文件不存在,告知客户端
self.request.recv() if __name__ == "__main__":
try:
IP,PORT = "localhost",
server = socketserver.ThreadingTCPServer((IP,PORT),MyTcpServer) #定义socketserver实例
server.serve_forever()
except KeyboardInterrupt as e:
print("关闭服务器")
上面代码是服务器端,客户端与服务器端其实是相呼应的,两者实现数据的交换;其实就是收发数据,中间掺杂我们想要实现的功能。
下面来看几个容易犯错的地方:
1、BrokenPipeError: [Errno 32] Broken pipe
客户端代码:
import socket,os,json,sys class Myclient(object):
'''定义客户端'''
def __init__(self):
'''定义socket()实例'''
self.client = socket.socket() #生成soket()实例 def connect(self,ip,port):
"""定义连接"""
self.client.connect((ip,port)) def interactive(self):
'''定义和用户交互'''
while True:
cmd = input("请输入指令>>:").strip() #用户输入指令
if len(cmd) == :
print("指令不能为空!!!")
continue #指令不能为空
cmd_str = cmd.split()[] #指令由两种形式
if hasattr(self,cmd_str): #判断指令是否存在
func = getattr(self,cmd_str) #指令存在,则获取对应的方法
func(cmd)
elif cmd_str == 'q':
break
else:
self.help()
continue def help(self):
msg = """
ls
pwd
cd
put filename
get filename
"""
print("指令名称",msg) def put(self,cmd):
'''定义上传数据接口'''
cmd_list = cmd.split()
if len(cmd_list) > :
'''指令是由指令名和文件名构成'''
filename = cmd_list[] #获取文件名
if os.path.isfile(filename): #检测上传的文件名是否存在
'''文件名存在,则要告诉服务器端上传的文件名,文件大小,并检测服务器是否有相应的方法'''
filesize = os.stat(filename).st_size
msg_dic = {
"action":"put",
"filename":filename,
"filesize":filesize
}
'''转换为字节码的形式进行传输'''
self.client.send(json.dumps(msg_dic).encode("utf-8")) #转换为json格式进行上传,便于服务器接收后处理
server_response = self.client.recv() #等待服务器传回信息,防止粘包
self.client.send("收到了".encode("utf-8"))
if int(server_response.decode("utf-8")):
'''根据客户端反馈,服务器端是否存在相同的文件名'''
file_exist = int(self.client.recv().decode("utf-8"))
if file_exist:
'''服务器端存在相应的文件'''
while True:
cover_flag = input("文件已存在,是否覆盖原文件(y/n):")
if cover_flag == "y":
self.client.send("y".encode("utf-8"))
break
elif cover_flag == "n":
new_filename = input("请输入新的文件名>>:")
self.client.send(("n "+new_filename).encode("utf-8"))
break
else:
print("您输入的指令有误,请重新输入!!!")
continue
else:
self.client.send("新创建".encode("utf-8")) '''上面准备工作完毕,开始传输文件'''
with open(filename,'rb') as f:
for line in f:
self.client.send(line) #发送数据
'''客户端等待服务器端传来消息,告知上传成功'''
response = self.client.recv()
print(response.decode("utf-8")) #数据是否上传成功,告知用户
else:
print("服务器端不存在相应的指令!!!") else:
print("要上传的文件名不存在!") else:
print("没有输入要上传的文件名!!!") def get(self,cmd):
'''从服务器端下载数据'''
cmd_list = cmd.split() #获取用户输入指令
if len(cmd_list) > : #是由指令和文件名构成
filename = cmd_list[]
msg_dic = {
"filename":filename,
"action":"get"
} #把指令封装成字典发送给服务器
self.client.send(json.dumps(msg_dic).encode("utf-8")) #把指令以json形式传给服务器
server_response = int(self.client.recv().decode("utf-8")) #接收服务端发挥的指令,判断是否支持此方法
self.client.send("收到指令!".encode("utf-8"))
if server_response:
file_exists = int(self.client.recv().decode("utf-8")) #下载文件存在与否标识符
self.client.send("收到标识符".encode("utf-8")) #告知服务器收到标识符,防止粘包
if file_exists:
'''文件存在,则准备接收数据,会接收服务器发送过来的文件大小'''
file_mess = json.loads(self.client.recv().decode("utf-8"))
self.client.send("文件信息接收成功,开始进行文件接收!".encode("utf-8"))
filesize = file_mess["filesize"]
while True:
'''确定文件名'''
if os.path.isfile(filename):
'''说明客户端存在文件,就要让用户选择是否覆盖'''
choice_cover = input("文件名重复,是否覆盖现有文件(y/n)>>:")
if choice_cover == "y":
filename = filename
break #覆盖文件之后退出循环
elif choice_cover == "n":
filename = input("请输入新的文件名>>:")
'''由于用户输入了新的用户名,我们不知道此文件是否重名,因此重新检测一下,确保不重名'''
continue
else:
filename = filename
break #得到文件名之后退出循环
recvive_size =
with open(filename,'wb') as file:
while recvive_size < filesize:
data = self.client.recv()
file.write(data)
recvive_size += len(data)
print("数据下载完成!!!")
self.client.send("接收完毕".encode("utf-8"))
else:
print("要下载的文件不存在!!!") else:
print("服务器不支持此功能!!!") else:
print("对不起,输入有误!")
self.help() if __name__ == "__main__":
try:
client = Myclient()
client.connect("localhost",)
client.interactive()
except KeyboardInterrupt as e:
print("客户端断开!!!",e)
服务器端:
'''定义服务器端'''
import socketserver,json,os class MyTcpServer(socketserver.BaseRequestHandler):
'''定义服务器端,socketserver,继承的是BaseRequestHandler类'''
def handle(self):
'''服务器端所有的功能都在handle()里面进行处理,因此接收数据也是在handle()中,只是处理的时候,调用下面模块而已'''
# while True:
data = self.request.recv()
if len(data) == :
print("客户端断开")
# break
msg_dic = json.loads(data.decode("utf-8")) #服务器端接收指令
cmd = msg_dic["action"]
if hasattr(self,cmd): #判断服务器是否有相应的指令
self.request.send("".encode("utf-8"))
self.request.recv()
func = getattr(self,cmd)
func(msg_dic)
else:
self.request.send("".encode("utf-8"))
self.request.recv() def put(self,msg_dic):
'''定义上传的服务器代码'''
filename = msg_dic['filename']
filesize = msg_dic["filesize"]
'''判断服务器端是否存在对应的文件名'''
recvive_size =
if os.path.isfile(filename):
'''如果服务器存在相应的文件名,则询问客户端是否覆盖'''
self.request.send("".encode("utf-8")) #文件存在,循环客户端是否覆盖
response = self.request.recv().decode("utf-8")
response = response.split()
'''如果用户让覆盖则覆盖,否则重新创建''' if response[] == "y":
'''覆盖'''
with open(filename,"wb") as f1:
while recvive_size < filesize:
data = self.request.recv()
f1.write(data)
recvive_size += len(data)
self.request.send("文件接收成功!".encode("utf-8")) else:
'''不覆盖,新创建'''
new_filename = response[]
with open(new_filename,'wb') as f:
while recvive_size < filesize:
data1 = self.request.recv()
f.write(data1)
recvive_size += len(data1)
self.request.send("文件接收成功!".encode("utf-8")) else:
'''如果服务器不存在相应文件名,则创建'''
self.request.send("".encode("utf-8"))
self.request.recv()
with open(filename,'wb') as f2:
while recvive_size < filesize:
data1 = self.request.recv()
f2.write(data1)
recvive_size += len(data1)
self.request.send("文件接收成功!".encode("utf-8")) def get(self,msg_dict):
'''基础交流结束,服务器支持文件下载功能,开始文件下载操作'''
filename = msg_dict["filename"]
if os.path.isfile(filename):
self.request.send("".encode("utf-8")) #文件存在告知客户端
self.request.recv()
filesize = os.stat(filename).st_size
'''首先告知客户端文件大小,让这边做好接收准备'''
file_mess = {
"filesize":filesize,
}
self.request.send(json.dumps(file_mess).encode("utf-8")) #以json格式发送给客户端
self.request.recv() #防止粘包,客户端回应服务器接收完毕
with open(filename,"rb") as f_obj:
for line in f_obj:
self.request.send(line)
self.request.recv() else:
self.request.send("".encode("utf-8")) #文件不存在,告知客户端
self.request.recv() if __name__ == "__main__":
try:
IP,PORT = "localhost",
server = socketserver.ThreadingTCPServer((IP,PORT),MyTcpServer) #定义socketserver实例
server.serve_forever()
except KeyboardInterrupt as e:
print("关闭服务器")
上面代码是我遇到的坑,客户端没有变,只变了服务器端接收的代码,因为socketserver.serve_forever()持续的响应链接。结果客户端输入命令如下:
请输入指令>>:gcx
指令名称
ls
pwd
cd
put filename
get filename 请输入指令>>:put gcx
文件已存在,是否覆盖原文件(y/n):y
文件接收成功!
请输入指令>>:put gcx
Traceback (most recent call last):
File "/home/zhuzhu/day8作业/FTP/Ftpclient/ftp_client.py", line , in <module>
client.interactive()
File "/home/zhuzhu/day8作业/FTP/Ftpclient/ftp_client.py", line , in interactive
func(cmd)
File "/home/zhuzhu/day8作业/FTP/Ftpclient/ftp_client.py", line , in put
self.client.send("收到了".encode("utf-8"))
BrokenPipeError: [Errno ] Broken pipe
上面客户端执行结果可以看出,第一次执行没有问题,程序成功的接收到了服务器下载的数据,但是第二次操作的时候,开始报错,提示BrokenPipeError,这是什么错误呢?
ThreadingHTTPServer 实现的 http 服务,如果客户端在服务器返回前,主动断开连接,则服务器端会报 [Errno 32] Broken pipe 错,并导致处理线程 crash.
上面说明,我们交互一次之后,服务器端已经断开了,不是说socketserver()的客户端一直处在活跃状态吗?是处在活跃状态没错,但是上一个链接其实已经断开了,这是socket的特性,如果没有程序接收数据,接收一次就会断开,因此要修改接收的代码,如下:
class MyTcpServer(socketserver.BaseRequestHandler):
'''定义服务器端,socketserver,继承的是BaseRequestHandler类'''
def handle(self):
'''服务器端所有的功能都在handle()里面进行处理,因此接收数据也是在handle()中,只是处理的时候,调用下面模块而已'''
while True:
data = self.request.recv()
if len(data) == :
print("客户端断开")
break
msg_dic = json.loads(data.decode("utf-8")) #服务器端接收指令
cmd = msg_dic["action"]
if hasattr(self,cmd): #判断服务器是否有相应的指令
self.request.send("".encode("utf-8"))
self.request.recv()
func = getattr(self,cmd)
func(msg_dic)
else:
self.request.send("".encode("utf-8"))
self.request.recv()
上面只需修改handle()中的代码,让服务器端能够持续不断的接收数据,如上面代码所示,加上一个while循环,让服务器能够不断接收此链接的信息,除非这个链接断开,否则是不会终端这个链接与服务端的交互,socketserver()实现的功能时多个客户端与服务端能够同时进行交互,使其相互之间不受影响,本质上单个客户端与服务器之间的交互还是基础的socket实现的,如果不持续的接收,那么交互一次就会断开。
上面的交互如下所示:
请输入指令>>:put gcx
文件已存在,是否覆盖原文件(y/n):y
文件接收成功!
请输入指令>>:put zmz
文件已存在,是否覆盖原文件(y/n):y
文件接收成功!
请输入指令>>:put gcx
文件已存在,是否覆盖原文件(y/n):y
文件接收成功!
请输入指令>>:客户端断开!!!
从上面代码可以看出,我们实现了持续的数据交换情况,没有发生太大的问题。
2、反射的时候,反射是判断类中是否具有某种方法,hasattr(),getattr()是最常使用的方法;
3、while a < b:
with open(filename) as f:
for line in f
与
wiht open(filename) as f:
while a < b:
for line in f
上面两种写法是不一样的,为什么说呢,第一种方法,当文件遍历玩的时候,不管条件成立与否,文件都是要关闭的,这是因为with打开文件具有自动关闭文件的特性,当文件遍历完成之后,就会自动关闭文件。
建议使用第二种方式,第二种方式就会杜绝这种情况,让程序能够即完成比较,由遍历完成文件。
4、socketserver与socket的区别,其实两者本质都是一样的,原则上都是交互一次结束,只是socketserver封装了很多方法,能够实现不相互干扰下的交互;
5、文件传输,要告知文件大小,方便接收,json的使用,序列化,让彼此接受的时候,容易得到之前存储的结果;
6、规范化封装;
day8--socketserver作业的更多相关文章
- python day33 ,socketserver多线程传输,ftp作业
一.一个服务端连多个客户端的方法 1.服务端 import socketserver class MyServer(socketserver.BaseRequestHandler): def hand ...
- python 全栈开发,Day36(作业讲解(大文件下载以及进度条展示),socket的更多方法介绍,验证客户端链接的合法性hmac,socketserver)
先来回顾一下昨天的内容 黏包现象粘包现象的成因 : tcp协议的特点 面向流的 为了保证可靠传输 所以有很多优化的机制 无边界 所有在连接建立的基础上传递的数据之间没有界限 收发消息很有可能不完全相 ...
- python全栈开发day29-网络编程之socket常见方法,socketserver模块,ftp作业
一.昨日内容回顾 1.arp协议含义 2.子网,子网掩码 3.两台电脑在网络中怎么通信的? 4.tcp和udp socket编码 5.tcp和udp协议的区别 6.tcp三次握手和四次挥手,syn洪攻 ...
- python2.0 s12 day8 _ socketserver学习
Socket 概念 一个socket就是一个点对点的链接.当今,大多数的通信都是基于Internet Protocl,因此大多数的网络Socket都是Internet Protocl(互联网)的通信( ...
- 老男孩Day8作业:FTP
1.作业需求 开发简单的FTP: 1. 用户登陆 2. 上传/下载文件 3. 不同用户家目录不同 4. 查看当前目录下文件 5. 充分使用面向对象知识 2.流程图 3.目录结构 4.代码区 bin目录 ...
- day8文件操作作业详解
1.day8题目 1,有如下文件,a1.txt,里面的内容为: 老男孩是最好的培训机构, 全心全意为学生服务, 只为学生未来,不为牟利. 我说的都是真的.哈哈 分别完成以下的功能: a,将原文件全部读 ...
- Day8作业及默写
1,有如下文件,a1.txt,里面的内容为: 老男孩是最好的培训机构, 全心全意为学生服务, 只为学生未来,不为牟利. 我说的都是真的.哈哈 分别完成以下的功能: 将原文件全部读出来并打印. with ...
- 实践作业3:白盒测试----第三次小组会DAY8
我们小组于12月11日在东九教学楼召开了会议,小组第二次会议中就讨论了被测系统中风险最高的模块,于是选择管理员的教师添加模块,针对代码展开静态评审.这一次会议,小组主要讨论了应该从哪些方面来测评代码的 ...
- day8作业
# 一:for循环 # 1.1 for循环嵌套之打印99乘法表 for i in range(1,10): for j in range(1,i+1): print("{} * {} = { ...
- Python之路,Day8 - Socket编程进阶
Python之路,Day8 - Socket编程进阶 本节内容: Socket语法及相关 SocketServer实现多并发 Socket语法及相关 socket概念 socket本质上就是在2台 ...
随机推荐
- html接收参数
代码 <!DOCTYPE html> <html> <head> <title>html接收参数</title> </head> ...
- WinRar 压缩接压缩文件
windows WinRAR 定时压缩文件 命名当天时间 设置时间格式: set "Ymd=%date:~,4%%date:~5,2%%date:~8,2%" 指定 WinRAR ...
- mysql 案例 ~ pt-io工具的使用
一 简介:如何使用pt-iopfile调查io具体信息二 目的:利用pt-iopfile分析mysql内部IO操作密集的文件,用以发现问题三 使用: pt-iopfile -p mysql_pid ...
- ajax大并发问题
今天在对项目做性能分析时发现,js代码中同时发出的多个异步请求耗时很长,查看服务器处理 时间发现,每个请求的响应都在毫秒级,但是页面请求的响应时间却在1秒左右,百思不得其解,后来仔细测试发现,这个并发 ...
- IDEA常用快捷键[转]
原文:http://www.cnblogs.com/wxdlut/p/3410541.html 查询快捷键CTRL+N 查找类CTRL+SHIFT+N 查找文件CTRL+SHIFT+ALT+N ...
- WPF开发中的多线程的问题
今天帮助同事做了一个WPF版的多线程demo,分享给大家. 要实现的问题就是非主线程thread1 去后台不停的取新数据,当有新数据的时候就会展示到前台. 我给他做的demo实现一个按秒的计数器,随着 ...
- python3数字、日期和时间
1.对数值进行取整 #使用内建的round(value,ndigits)函数来取整,ndigits指定保留的位数,在取整时会取值在偶数上,如1.25取一位会取整1.2,1.26会取整1.3 In [1 ...
- Word打开默认显示缩略图,而不是文档结构图
So easy! 1.打开Word文档,点击缩略图右侧的"X",关闭缩略图: 2.打开菜单[视图],勾选"文档结构图": 3.关闭当前Word文档: 4.再次打 ...
- 在全志平台调试博通的wifi驱动(类似ap6212)【转】
转自:http://blog.csdn.net/fenzhi1988/article/details/44809779 调试驱动之前,首先先看看驱动代码,了解代码大致工作流程,再根据硬件配置驱动,比如 ...
- 存储器结构、cache、DMA架构分析--【原创】
存储器的层次结构 高速缓冲存储器 cache 读cache操作 cache如果包含数据就直接从cache中读出来,因为cache速度要比内存快 如果没有包含的话,就从内存中找 ...