在Python中将UDP数据写入CSV?

时间:2013-07-09 21:26:31

标签: python csv encoding udp ascii

免责声明:我是一个完整的Python n00b,从来没有用Python编写任何东西,我几年没有编写任何东西,我学到的最后一种语言是Visual Basic 6.所以请耐心等待!

所以我有一个Android应用程序,通过UDP将我的手机传感器(加速度计,磁铁,光线等)数据传输到我的Windows PC,我有一个Python 3.3脚本在屏幕上显示该数据,并将其写入CSV :

#include libraries n stuff
import socket
import traceback
import csv

#assign variables n stuff
host = ''
port = 5555
csvf = 'accelerometer.csv'

#do UDP stuff
s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
s.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
s.setsockopt(socket.SOL_SOCKET, socket.SO_BROADCAST, 1)
s.bind((host, port))

#do CSV stuff
with open(csvf, 'w', newline='', encoding='ascii') as csv_handle:
    csv_writer = csv.writer(csv_handle, delimiter=',')
    while 1:
        try:
            message, address = s.recvfrom(8192) 
            print(message)                      #display data on screen
            csv_writer.writerow(message)        #write data to CSV
        except(KeyboardInterrupt, SystemExit):  
            raise
        except:
            traceback.print_exc()               

屏幕上的数据如下所示,这是正确的:

b'7407.75961, 3, 0.865, 1.423, 9.022, 5,

CSV文件中的数据看起来像数据的ASCII代码的数值(注意:代码与上面的代码不匹配,因为数据略有不同):

57,48,48,50,46,54,51,57,57,57,44,32,51,44,32,32,32,48,46,53,52,57,44,32,32,53,46,54,56,56,44,32,32,56,46,51,53,53

如何让我的CSV只写UDP套接字接收的字符串?正如你所看到的那样,我尝试添加“encoding ='ascii'”,但这并没有区别于它。

2 个答案:

答案 0 :(得分:0)

尝试:

csv_writer.writerow([message])

csv_writer.writerow期望一个iterable作为它的第一个参数,它将是逗号分隔值的列表。在您的示例中,消息是一个字符串,它是可迭代的,因此csv_writer将每个字符写入单独的逗号分隔值。

答案 1 :(得分:0)

writerow需要一个序列或可迭代的值。但你只有一个价值。

它起作用的原因,但做错了,是你的一个值 - 一个bytes字符串 - 实际上本身就是一个序列。但它不是逗号分隔值的序列,而是一个字节序列。

那么,你如何获得一系列单独的值?


一种选择是使用split。这里message.split(b', ')map(str.strip, message.split(b','))似乎合理。那会给你这个序列:

[b'7407.75961', b'3', b'0.865', b'1.423', b'9.022', b'5']

但实际上,这正是csv模块的用途。例如,您可以将输入包装在BytesIO中并将其传递给csv.reader,然后您只需将reader中的行复制到writer


但是如果您考虑一下,那么您将获得csv格式的数据,并且您希望以完全相同的csv格式写出数据,而不是以任何其他方式使用它......所以你甚至不需要 csv模块。只需使用普通的旧二进制文件:

with open(csvf, 'wb') as csv_handle:
    while True:
        try:
            message, address = s.recvfrom(8192) 
            print(message)                      #display data on screen
            csv_handle.write(message + b'\n')
        except(KeyboardInterrupt, SystemExit): 
            raise
        except:
            traceback.print_exc()

虽然我们正在努力,但你几乎不需要这样做:

except(KeyboardInterrupt, SystemExit): 
    raise
except:
    traceback.print_exc()

Python 3.x中唯一不从Exception继承的例外是KeyboardInterruptSystemExitGeneratorExit(这里不可能发生),以及任何第三方例外情况,例如KeyboardInterruptSystemExit。所以,就这样做:

except Exception:
    traceback.print_exc()