LINUX.ORG.RU

Python передача списка по сети.

 ,


0

1

Доброго времени суток!
Заранее извиняюсь за нубский вопрос, но не могу сформулировать правильный запрос в гугл.

Хочу передать по сети переменные типа список. Причем, как вида:
>data = [ 'asdf', 'qwer', 'zxcv', '0']
так и вида
>data1 = [['asdf', 'qwer'], '0', '0']
И более сложные.
Застопорился уже на первом. Передать как
>client_socket.send(data)
Нельзя, требует строку или буфер. Передаю как:
>client_socket.send(str(data).encode(«utf-8»))
Принимаю так:
>data = client_sock.recv(256).decode(«utf-8»)
Теперь фокус в том, что data теперь — текстовая строка, а не список.
Как превратить в список или как передавать не строкой?

★★★★★
Ответ на: комментарий от eb

А какого вида получается строка. Например?

Например: «[ 'asdf', 'qwer', 'zxcv', '0']»

fractaler ★★★★★
() автор топика
Ответ на: комментарий от Hope

еще длину строки с данными надо передавать вообще то.

AIv ★★★★★
()
Ответ на: комментарий от pztrn

Это pickle то ненужная зависимость?

Жсон явно медленнее и данные могут восстановиться не такими какими они были (кортеж например сериализуется в массив и десериализуется в питоновый массив соответственно). Да и скорее всего избыточен для задачи ТС.

В общем случае согласен, жсон во все поля.

Kalashnikov ★★★
()
Ответ на: комментарий от pztrn
$ python
Python 2.6.6 (r266:84292, Dec 26 2010, 22:31:48) 
[GCC 4.4.5] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>> import json
>>> json.dumps( range(10))
'[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]'
>>> class A : pass
... 
>>> json.dumps( A() )
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "/usr/lib/python2.6/json/__init__.py", line 230, in dumps
    return _default_encoder.encode(obj)
  File "/usr/lib/python2.6/json/encoder.py", line 367, in encode
    chunks = list(self.iterencode(o))
  File "/usr/lib/python2.6/json/encoder.py", line 317, in _iterencode
    for chunk in self._iterencode_default(o, markers):
  File "/usr/lib/python2.6/json/encoder.py", line 323, in _iterencode_default
    newobj = self.default(o)
  File "/usr/lib/python2.6/json/encoder.py", line 344, in default
    raise TypeError(repr(o) + " is not JSON serializable")
TypeError: <__main__.A instance at 0x7f7c6ca954d0> is not JSON serializable
>>> import pickle
>>> pickle.dumps( A() )
'(i__main__\nA\np0\n(dp1\nb.'
>>> 

И после этого кто то ругает pickle и хвалит json?

AIv ★★★★★
()
Ответ на: комментарий от AIv

И после этого кто то ругает pickle и хвалит json?

Python 2.7.3 (default, Aug  1 2012, 05:14:39) 
[GCC 4.6.3] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>> import ctypes, pickle
>>> pickle.dumps(ctypes.c_voidp(0))
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "/usr/lib/python2.7/pickle.py", line 1374, in dumps
    Pickler(file, protocol).dump(obj)
  File "/usr/lib/python2.7/pickle.py", line 224, in dump
    self.save(obj)
  File "/usr/lib/python2.7/pickle.py", line 306, in save
    rv = reduce(self.proto)
ValueError: ctypes objects containing pointers cannot be pickled

Какой же тут напрашивается вывод? Очевидно ни json, ни pickle пользоваться ни в коем случае нельзя.

nozh
()
Ответ на: комментарий от nozh

Уж поактуальней бы пример привели, типа lambda функции, или пользовательского С++ класса подключенного через SWIG

AIv ★★★★★
()
Ответ на: комментарий от nozh

Вы что, никогда не сталкивались с необходимостью сохранить/передать экземпляр пользовательского класса? Вообще то это типовая задача, в отличии от передачи/сохранения указателя (который на принмающей стороне либо после восстановления с диска скорей всего будет невалиден). Ну уж если так приперло - сериализуйте как число, проблем нет.

AIv ★★★★★
()
Ответ на: комментарий от AIv

Вы что, никогда не сталкивались с необходимостью сохранить/передать экземпляр пользовательского класса? Вообще то это типовая задача, в отличии от передачи/сохранения указателя (который на принмающей стороне либо после восстановления с диска скорей всего будет невалиден). Ну уж если так приперло - сериализуйте как число, проблем нет.

Хорошо, а если мне нужно сериализовать пользовательский C++ класс, подключённый через SWIG? :)

nozh
()
Ответ на: комментарий от nozh

ВОт там все сложнее, поскольку в питоне видна только свиговая обертка с перегруженными __get/setattr__, и понадобиться чуть чуть поколдовать. Если и правда интересно - вот тут http://a-iv.ru/pyart/cpp2py.pdf, 5й раздел.

Хочу отметить, что это уже НЕ типовая задача, но таки и она решается с минимальными усилиями. Я с json никогда не работал, подозреваю что его таки можно заставить сериализовывать и классы, но то что это требует каких то доп. телодвижений удивляет (мягко говоря).

AIv ★★★★★
()
Ответ на: комментарий от Kalashnikov

pickle тут вроде подойдёт.

Спасибо! pickle подошёл отлично.

Остальную дискуссию тоже интересно оказалось прочитать, но пока что я ухватился за первое рабочее решение. Тем более, что программка у меня пока простенькая и никаких хитростей, кроме собственных ошибок не должно быть.

fractaler ★★★★★
() автор топика

соедини элементы списка в строку через разделитель, а потом split по тому же разделителю.

XoFfiCEr ★★☆☆
()
data = [ 'asdf', 'qwer', 'zxcv', '0']
razd='@'
string=data[0]+razd+data[1]+razd+data[2]+razd+data[3]
#...................................................................................................
#и
data=string.split('@')
XoFfiCEr ★★☆☆
()
Последнее исправление: XoFfiCEr (всего исправлений: 1)
Ответ на: комментарий от XoFfiCEr

И на выходе ты получишь

[«'asdf'», «'qwer'», «'zxcv'», «'0'»]

И это мы ещё не говорили о вложенных списках и кортежах. Конечно, через split() и strip() можно распарсить одномерный список. Но вложенные списки уже проблема.
Кстати, для вставки разделителя есть join()

fractaler ★★★★★
() автор топика
Ответ на: комментарий от fractaler

Я и писал для одномерного массива, для вложенных списков процедура немного сложнее.

XoFfiCEr ★★☆☆
()
Ответ на: комментарий от XoFfiCEr

если такие знаки есть, то другой разделитель нужен. Что тут непонятного?

попросить пользователя не слать запретные символы?

sp3
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.