【发布时间】:2016-02-18 14:37:59
【问题描述】:
我正在尝试通过套接字连接向服务器发送 numpy.array。我发现了一个我似乎无法理解的行为:我使用 pickle.dumps 来获取我的数组对象的字符串表示,并使用 sys.getsizeof 来估计需要传输的字节数。但是,无论输入的大小如何,我的代码似乎都将数据字符串的长度高估了 37 个字节。
服务器代码:
def recvall(sock, count):
buf = b''
while count:
newbuf = sock.recv(count)
if not newbuf: return None
buf += newbuf
count -= len(newbuf)
print 'left to read: %i' %count
return buf
if __name__ == '__main__':
serversocket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
serversocket.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
serversocket.bind((socket.gethostname(), 8089)) #visible to the outside world?
serversocket.listen(5) # become a server socket, maximum 5 connections
while True:
connection, address = serversocket.accept()
#read message size
buf = recvall(connection, 4)
bytes_to_read, = struct.unpack('!I', buf)
print 'Message size: %i' % bytes_to_read
#read message
buf = recvall(connection, bytes_to_read - 37) #HACK: no idea why is that: size is overestimated by 37?!
connection.close()
reconstructed = pickle.loads(buf);
img.imsave('out.png', reconstructed);
print reconstructed.shape
客户端代码:
#read image
im = img.imread(sys.argv[1])
im_str = pickle.dumps(im)
#### communication
clientsocket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
clientsocket.connect(('ororea', 8089))
tmp = struct.pack('!I', int(sys.getsizeof(im_str))); #unsigned int
#print sys.getsizeof(tmp)
clientsocket.sendall(tmp)
clientsocket.sendall(im_str);
clientsocket.close()
像这样,传输成功了,但我不明白为什么少发送了 37 个字节。
最好的问候, 多米尼克
【问题讨论】:
-
输入、数据包和输出是什么样的?
-
你应该使用
len,而不是sys.getsizeof。 -
@falsetru:谢谢,这解决了问题。我在套接字连接的教程中发现了这一点。刚在API里查了一下,也找到了解释:
getsizeof()调用了对象的__sizeof__方法,如果对象是由垃圾回收器管理的,就会增加额外的垃圾回收器开销。