1

私はこの機能を使用しようとしています:

import unicodedata

def remove_accents(input_str):
    nkfd_form = unicodedata.normalize('NFKD', unicode(input_str))
    return u"".join([c for c in nkfd_form if not unicodedata.combining(c)])

以下のコード (非 ASCII 文字列を含むファイルを解凍して読み取る)。しかし、このエラーが発生しています(このライブラリファイルからC:\Python27\Lib\encodings\utf_8.py):

Message File Name   Line    Position    
Traceback               
    <module>    C:\Users\CG\Desktop\Google Drive\Sci&Tech\projects\naivebayes\USSSALoader.py    64      
    getNameList C:\Users\CG\Desktop\Google Drive\Sci&Tech\projects\naivebayes\USSSALoader.py    26      
    remove_accents  C:\Users\CG\Desktop\Google Drive\Sci&Tech\projects\naivebayes\USSSALoader.py    17      
UnicodeDecodeError: 'ascii' codec can't decode byte 0xe1 in position 3: ordinal not in range(128)

このエラーが発生するのはなぜですか? それを回避して機能させる方法はremove_accents

助けてくれてありがとう!

コード全体は次のとおりです。

#!/usr/bin/env python

# -*- coding: utf-8 -*-
# -*- coding: utf-8 -*-

import os
import re
from zipfile import ZipFile
import csv

##def strip_accents(s):
##   return ''.join((c for c in unicodedata.normalize('NFD', s) if unicodedata.category(c) != 'Mn'))

import unicodedata

def remove_accents(input_str):
    nkfd_form = unicodedata.normalize('NFKD', unicode(input_str))
    return u"".join([c for c in nkfd_form if not unicodedata.combining(c)])

def getNameList():
    namesDict=extractNamesDict()
    maleNames=list()
    femaleNames=list()
    for name in namesDict:
        print name
#        name = strip_accents(name)
        name = remove_accents(name)
        counts=namesDict[name]
        tuple=(name,counts[0],counts[1])
        if counts[0]>counts[1]:
            maleNames.append(tuple)
        elif counts[1]>counts[0]:
            femaleNames.append(tuple)
    names=(maleNames,femaleNames)
 #   print maleNames
    return names

def extractNamesDict():
    zf=ZipFile('names.zip', 'r')
    filenames=zf.namelist()

    names=dict()
    genderMap={'M':0,'F':1}

    for filename in filenames:
        file=zf.open(filename,'r')
        rows=csv.reader(file, delimiter=',')

        for row in rows:
            #name=row[0].upper().decode('latin1')
            name=row[0].upper()
            gender=genderMap[row[1]]
            count=int(row[2])

            if not names.has_key(name):
                names[name]=[0,0]
            names[name][gender]=names[name][gender]+count

        file.close()
  #      print '\tImported %s'%filename
   # print names
    return names

if __name__ == "__main__":
    getNameList()
4

3 に答える 3

3

文字列内のUnicode文字をASCIIに堅牢に変換する場合は、すばらしいUnicodeモジュールを使用する必要があります。

>>> import unidecode
>>> unidecode.unidecode(u'Björk')
'Bjork'
>>> unidecode.unidecode(u'András Sütő')
'Andras Suto'
>>> unidecode.unidecode(u'Ελλάς')
'Ellas'
于 2012-08-18T16:55:20.213 に答える
3

ベスト プラクティスは、データがプログラムに入ったときに Unicode にデコードすることです。

for row in rows:
    name=row[0].upper().decode('utf8') # or whatever...you DO need to know the encoding.

次にremove_accents、次のようになります。

def remove_accents(input_str):
    nkfd_form = unicodedata.normalize('NFKD', input_str)
    return u''.join(c for c in nkfd_form if not unicodedata.combining(c))

ファイル、データベース、端末などへの書き込みなど、プログラムを終了するときにデータをエンコードします。

そもそもアクセントを削除するのはなぜですか?

于 2012-08-18T02:39:04.877 に答える
2

コーデックを指定せずにバイト文字列からデコードしているため、取得できます。

unicode(input_str)

そこにコーデックを追加します (ここでは、データが utf-8 でエンコードされていると仮定します0xe1。3 バイト文字の最初の文字になります):

unicode(input_str, 'utf8')
于 2012-08-18T00:39:29.190 に答える