2012-02-07 41 views
4

我需要Python的模擬這個Perl的字符串:解壓格式字符在Python

unpack("nNccH*", string_val) 

我需要nNccH* - 在Python中字符格式的數據格式。

在Perl它解壓縮的二進制數據,以五個變量:在 「網絡」(大端) 「網絡」 在

  • 32位值(大端)
    • 16位值符號字符(8位整數)值
    • 符號字符(8位整數)值
    • 十六進制串,高半字節先

    但我不能這樣做在Python

    更多:

    bstring = '' 
    while DataByte = client[0].recv(1): 
        bstring += DataByte 
    print len(bstring) 
    if len(bstring): 
        a, b, c, d, e = unpack("nNccH*", bstring) 
    

    我從來沒有在Perl或Python寫的,但我現在的任務是寫這是用Perl編寫的多線程Python的服務器.. 。

  • +0

    我能找到除了H *之外的所有其他東西,我假設你會玩P或S。 – 2012-02-07 12:52:24

    +0

    您將需要計算字符串大小,這個答案可能會有所幫助。 http://stackoverflow.com/a/5849224/70350 – pojo 2012-02-07 12:54:16

    +0

    ' 「而數據字節=客戶端[0] .recv(1):」'是不Python的。這是行不通的。 – 2012-02-07 13:17:19

    回答

    7

    Perl的格式"nNcc"相當於Python的格式"!HLbb"。 Perl的"H*"在Python中沒有直接的等價物。

    有兩個問題。

    • Python的struct.unpack不接受通配符,*
    • Python的struct.unpack不「hexlify」數據串

    第一個問題可以用一個輔助函數一樣unpack圍繞工作 - 。

    第二個問題可以利用binascii.hexlify解決:

    import struct 
    import binascii 
    
    def unpack(fmt, data): 
        """ 
        Return struct.unpack(fmt, data) with the optional single * in fmt replaced with 
        the appropriate number, given the length of data. 
        """ 
        # http://stackoverflow.com/a/7867892/190597 
        try: 
         return struct.unpack(fmt, data) 
        except struct.error: 
         flen = struct.calcsize(fmt.replace('*', '')) 
         alen = len(data) 
         idx = fmt.find('*') 
         before_char = fmt[idx-1] 
         n = (alen-flen)//struct.calcsize(before_char)+1 
         fmt = ''.join((fmt[:idx-1], str(n), before_char, fmt[idx+1:])) 
         return struct.unpack(fmt, data) 
    
    data = open('data').read() 
    x = list(unpack("!HLbbs*", data)) 
    # x[-1].encode('hex') works in Python 2, but not in Python 3 
    x[-1] = binascii.hexlify(x[-1]) 
    print(x) 
    

    當在由此Perl腳本產生的數據進行測試:

    $line = pack("nNccH*", 1, 2, 10, 4, '1fba'); 
    print "$line"; 
    

    的Python腳本產生

    [1, 2, 10, 4, '1fba'] 
    
    +1

    +1,這個答案應該被接受:) – 2012-02-07 13:35:31

    +0

    'binascii.hexlify()'的替代方法是'str.encode(「hex」)''。 – 2012-02-07 13:48:53

    +0

    謝謝sooo多! – 2012-02-07 13:53:59

    6

    你要找的等效Python的功能是struct.unpack。格式字符串的文件是在這裏:http://docs.python.org/library/struct.html

    你必須得到幫助,如果你確實說明你需要什麼樣的拆包一個更好的機會。不是每個人都知道Perl。

    +0

    謝謝。我已經閱讀了perl和python解包文檔。但到目前爲止,我不明白一些時刻。 – 2012-02-07 12:40:34

    +0

    @Eli - 直接翻譯可能會遇到小問題。例如,如何在python中做H *?我猜,用戶本可以更好地回答這個問題。 – 2012-02-07 12:46:16

    +0

    @SenthilKumaran:請注意,用戶在我的回答後編輯了問題*。編輯之前,他沒有在Perl – 2012-02-07 13:01:55