2014-06-11 238 views
2

我正在使用Tweepy傳輸推文,並且希望將它們記錄爲CSV格式,以便我可以隨時播放它們或稍後將它們加載到數據庫中。 請記住,我是一個noob,但我知道有多種方式來處理這個問題(建議非常受歡迎)。在Python中將多個JSON寫入CSV - 將字典轉換爲CSV

長話短說,我需要將多個Python字典轉換並追加到一個CSV文件中。 我已經做了我的研究(How do I write a Python dictionary to a csv file?),並嘗試用DictWriter和writer方法做這件事。

然而,有需要完成一些事情:

1)寫鍵頭只有一次。

2)當新的tweet被流式傳輸時,需要附加值而不覆蓋以前的行。

3)如果值缺失記錄NULL。

4)跳過/修復ascii編解碼器錯誤。

這裏是我想與落得什麼樣的格式(每個價值就在於單個電池):

Header1_Key_1 Header2_Key_2 Header3_Key_3 ...

Row1_Value_1 Row1_Value_2 Row1_Value_3 ...

Row2_Value_1 Row2_Value_2 Row2_Value_3 ...

Row3_Value_1 Row3_Value_2 Row3_Value_3 ...

滾裝w4_Value_1 Row4_Value_2 Row4_Value_3 ...

這裏是我的代碼:

from tweepy.streaming import StreamListener 
from tweepy import OAuthHandler 
from tweepy import Stream 
import csv 
import json 

consumer_key="XXXX" 
consumer_secret="XXXX" 
access_token="XXXX" 
access_token_secret="XXXX" 

class StdOutListener(StreamListener): 

    def on_data(self, data): 
     json_data = json.loads(data) 

     data_header = json_data.keys() 
     data_row = json_data.values() 

     try: 
      with open('csv_tweet3.csv', 'wb') as f: 
       w = csv.DictWriter(f, data_header) 
       w.writeheader(data_header) 
       w.writerow(json_data) 
     except BaseException, e: 
      print 'Something is wrong', str(e) 

     return True 

    def on_error(self, status): 
     print status 

if __name__ == '__main__': 
    l = StdOutListener() 
    auth = OAuthHandler(consumer_key, consumer_secret) 
    auth.set_access_token(access_token, access_token_secret) 

    stream = Stream(auth, l) 
    stream.filter(track=['world cup']) 

預先感謝您!

+0

你是說你有什麼不工作?另外,你總是可以將json轉儲到一個文件中,每行一個條目... – monkut

+0

這不起作用。是的,你可以,但我想獲得csv格式。 – verkter

+1

當你說它'不工作',有什麼具體的,似乎並沒有工作。例如,是否有例外? – monkut

回答

1

我用facebook的圖形API(facepy模塊)做了類似的事情!

from tweepy.streaming import StreamListener 
from tweepy import OAuthHandler 
from tweepy import Stream 
import csv 
import json 

consumer_key="XXXX" 
consumer_secret="XXXX" 
access_token="XXXX" 
access_token_secret="XXXX" 

class StdOutListener(StreamListener): 
    _headers = None 
    def __init__(self,headers,*args,**keys): 
     StreamListener.__init__(self,*args,**keys) 
     self._headers = headers 

    def on_data(self, data): 
     json_data = json.loads(data) 

     #data_header = json_data.keys() 
     #data_row = json_data.values() 

     try: 
      with open('csv_tweet3.csv', 'ab') as f: # a for append 
       w = csv.writer(f) 
       # write! 
       w.writerow(self._valToStr(json_data[header]) 
          if header in json_data else '' 
          for header in self._headers) 
     except Exception, e: 
      print 'Something is wrong', str(e) 

     return True 

    @static_method 
    def _valToStr(o): 
     # json returns a set number of datatypes - parse dependingly 
     # https://docs.python.org/2/library/json.html#encoders-and-decoders 
     if type(o)==unicode: return self._removeNonASCII(o) 
     elif type(o)==bool: return str(o) 
     elif type(o)==None: return '' 
     elif ... 
     ... 

    def _removeNonASCII(s): 
     return ''.join(i if ord(i)<128 else '' for i in s) 

    def on_error(self, status): 
     print status 

if __name__ == '__main__': 
    headers = ['look','at','twitter','api', 
       'to','find','all','possible', 
       'keys'] 

    # initialize csv file with header info 
    with open('csv_tweet3.csv', 'wb') as f: 
     w = csv.writer(headers) 

    l = StdOutListener(headers) 
    auth = OAuthHandler(consumer_key, consumer_secret) 
    auth.set_access_token(access_token, access_token_secret) 

    stream = Stream(auth, l) 
    stream.filter(track=['world cup']) 

這不是複製粘貼&準備好了,但它是不夠清楚的地方,你應該能夠完成它。
對於性能,您可能希望查看打開文件,寫入多個記錄,然後關閉文件。這樣你不會一直打開,初始化csv編寫器,追加,然後關閉文件。我對tweepy API並不熟悉,所以我不確定這將如何工作 - 但值得深入研究。

如果遇到任何麻煩,我會很樂意幫助 - 享受!