4

私は長い間このエラーで立ち往生していました:

 TypeError: expected a character buffer object

私は誤解していることを理解しています。これは、Unicode文字列と「単純な」文字列の違いに関するものです。上記のコードを「通常の」文字列で使用しようとしましたが、Unicode文字列を渡す必要がありました。したがって、文字列が実行を中断する前の単純な「u」を忘れてしまいます:/ !!!

ところで、TypeErrorは私には非常に不明確であり、今でもそうです。

何が欠けていたのか、なぜ「単純な」文字列が「文字バッファオブジェクト」ではないのかを説明してもらえますか?

以下のコードで再現できます(ここから抽出して(c):)

def maketransU(s1, s2, todel=u""):
    """Build translation table for use with unicode.translate().

    :param s1: string of characters to replace.
    :type s1: unicode
    :param s2: string of replacement characters (same order as in s1).
    :type s2: unicode
    :param todel: string of characters to remove.
    :type todel: unicode
    :return: translation table with character code -> character code.
    :rtype: dict
    """
    # We go unicode internally - ensure callers are ok with that.
    assert (isinstance(s1,unicode))
    assert (isinstance(s2,unicode))
    trans_tab = dict( zip( map(ord, s1), map(ord, s2) ) )
    trans_tab.update( (ord(c),None) for c in todel )
    return trans_tab

#BlankToSpace_table = string.maketrans (u"\r\n\t\v\f",u"     ")
BlankToSpace_table = maketransU (u"\r\n\t\v\f",u"     ")
def BlankToSpace(text) :
    """Replace blanks characters by realspaces.

    May be good to prepare for regular expressions & Co based on whitespaces.

    :param  text: the text to clean from blanks.
    :type  text: string
    :return: List of parts in their apparition order.
    :rtype: [ string ]
    """
    print text, type(text), len(text)
    try:
        out =  text.translate(BlankToSpace_table)
    except TypeError, e:
        raise
    return out

# for SO : the code below is just to reproduce what i did not understand
dummy = "Hello,\n, this is a \t dummy test!"
for s in (unicode(dummy), dummy):
    print repr(s)
    print repr(BlankToSpace(s))

生産:

u'Hello,\n, this is a \t dummy test!'
Hello,
, this is a      dummy test! <type 'unicode'> 32
u'Hello, , this is a   dummy test!'
'Hello,\n, this is a \t dummy test!'
Hello,
, this is a      dummy test! <type 'str'> 32

Traceback (most recent call last):
  File "C:/treetaggerwrapper.error.py", line 44, in <module>
    print repr(BlankToSpace(s))
  File "C:/treetaggerwrapper.error.py", line 36, in BlankToSpace
    out =  text.translate(BlankToSpace_table)
TypeError: expected a character buffer object
4

1 に答える 1

12

問題は、バイト文字列のメソッドがユニコード文字列translateのメソッドとは異なることです。translate非ユニコードバージョンのdocstringは次のとおりです。

S.translate(table [、deletechars])->文字列

文字列Sのコピーを返します。ここで、オプションの引数deletecharsに含まれるすべての文字が削除され、残りの文字は指定された変換テーブルを介してマップされます。これは長さ256の文字列である必要があります。

そして、これがユニコードバージョンです:

S.translate(table)-> unicode

文字列Sのコピーを返します。ここで、すべての文字は指定された変換テーブルを介してマッピングされています。これは、Unicode序数からUnicode序数、Unicode文字列、またはNoneへのマッピングである必要があります。マップされていない文字はそのまま残されます。Noneにマップされた文字は削除されます。

非Unicodeバージョンは「長さ256の文字列」を期待しているのに対し、非Unicodeバージョンは「マッピング」(つまりdict)を期待していることがわかります。したがって、問題は、Unicode文字列がバッファオブジェクトであり、非Unicode文字列がそうではないということではありません-もちろん、両方ともバッファです-しかし、一方のtranslateメソッドはそのようなバッファオブジェクトを期待し、もう一方はそうではありません。

于 2012-04-30T14:39:45.130 に答える