2014-10-15 6 views
6

पर एक बहुआयामी numpy सरणी भेजें अच्छा दिन,सॉकेट

मैंने इसकी खोज की है लेकिन किसी भी प्रतिक्रिया के साथ नहीं आया है। मैं एक सॉकेट पर एक बहु आयामी numpy सरणी भेजना चाहता हूँ। इसलिए, मैं इसे एक स्ट्रिंग में बदलने का फैसला किया:

>>> import numpy as np 
>>> x = np.array([[0, 1], [2, 3]]) 
>>> xstring = x.tostring() 
>>> print xstring 

>>> print x 
[[0 1] 
[2 3]] 
>>> print xstring 

>>> nparr = np.fromstring(xstring, dtype=np.uint8) 
>>> print nparr 
[0 0 0 0 0 0 0 0 1 0 0 0 0 0 0 0 2 0 0 0 0 0 0 0 3 0 0 0 0 0 0 0] 

वहाँ वैसे भी है मैं, करने के लिए किसी भी तरह स्ट्रिंग के लिए रूपांतरण प्राप्त कर सकते हैं इसके बारे में आयाम को बचाने:

हालांकि, यह सरणी के प्रतिनिधित्व को नष्ट कर देता ?

उत्तर

2

दरअसल, .tostring केवल कच्चा डेटा लौटाता है। इसका मतलब यह है कि यदि आप दूसरी तरफ ज्ञात नहीं हैं तो आपको अतिरिक्त रूप से सरणी के आकार और प्रकार को भेजने की आवश्यकता है।

हो सकता है कि इसे का उपयोग सरणी क्रमानुसार करने आसान है अचार:

import numpy as np 
from cPickle import dumps, loads 

x = np.array([[1, 2],[3, 4]], np.uint8) 
print loads(dumps(x)) 
# [[1 2] 
# [3 4]] 

हालांकि बहुत छोटे सरणियों के लिए आकार भूमि के ऊपर महत्वपूर्ण हो सकता है:

print len(x.tostring()), len(dumps(x)) 
# 4 171 

अचार का उपयोग कर के बारे में अधिक के लिए, see here.

+0

अचार बहुत धीमा था, और मेरे 2 डी सरणी बड़े पैमाने पर बना दिया। यह कभी-कभी मेरे कार्यक्रम को कुछ महत्वपूर्ण आतंकवादियों के साथ दुर्घटनाग्रस्त कर देता है – ovfstack

+0

@ovfstack: आप सही हैं। पायथन 3 पर ओवरहेड बड़े सरणी के लिए नगण्य है और यह '.osting()' के रूप में धीमा गति से दोगुना चलता है। पाइथन 2 के लिए आपको एक बड़ा सुधार देखना चाहिए यदि आप 'प्रोटोकॉल = 2' निर्दिष्ट करते हैं, हालांकि यह अभी भी इस मामले में '.osting()' से 4 गुना धीमा प्रतीत होता है। –

+0

मैंने अभी आईकनकोड फ़ंक्शन का उपयोग किया है जो opencv प्रदान करता है। यह मेरी सरणी को "संपीड़ित" करने में भी सक्षम था और imdecode सभ्य सटीकता के साथ इसे पुनर्प्राप्त करने में सक्षम था – ovfstack

5

इस उदाहरण को आजमाएं: -

import socket 
import numpy as np 
from cStringIO import StringIO 

class numpysocket(): 
    def __init__(self): 
     pass 

    @staticmethod 
    def startServer(): 
     port=7555 
     server_socket=socket.socket() 
     server_socket.bind(('',port)) 
     server_socket.listen(1) 
     print 'waiting for a connection...' 
     client_connection,client_address=server_socket.accept() 
     print 'connected to ',client_address[0] 
     ultimate_buffer='' 
     while True: 
      receiving_buffer = client_connection.recv(1024) 
      if not receiving_buffer: break 
      ultimate_buffer+= receiving_buffer 
      print '-', 
     final_image=np.load(StringIO(ultimate_buffer))['frame'] 
     client_connection.close() 
     server_socket.close() 
     print '\nframe received' 
     return final_image 

    @staticmethod 
    def startClient(server_address,image): 
     if not isinstance(image,np.ndarray): 
      print 'not a valid numpy image' 
      return 
     client_socket=socket.socket() 
     port=7555 
     try: 
      client_socket.connect((server_address, port)) 
      print 'Connected to %s on port %s' % (server_address, port) 
     except socket.error,e: 
      print 'Connection to %s on port %s failed: %s' % (server_address, port, e) 
      return 
     f = StringIO() 
     np.savez_compressed(f,frame=image) 
     f.seek(0) 
     out = f.read() 
     client_socket.sendall(out) 
     client_socket.shutdown(1) 
     client_socket.close() 
     print 'image sent' 
     pass 

इस मॉडल में क्लाइंट सर्वर पर बहुआयामी ndarray भेजता है। दो कार्य शुरू होते हैं सर्वर() और startClient()। स्टार्टसेवर कोई तर्क नहीं लेता है लेकिन स्टार्ट क्लाइंट को सर्वर पते के साथ-साथ ndarray को तर्क के रूप में भी चाहिए। पहले सर्वर प्रारंभ करें और फिर क्लाइंट प्रारंभ करें। क्लाइंट से शटडाउन संदेश प्राप्त करने के बाद सर्वर बफर से पढ़ना शुरू कर देता है।