перебирать строки Юникода и сравнивать с Юникодом в словаре Python - PullRequest
9 голосов
/ 07 августа 2011


У меня есть два словаря python, содержащие информацию о японских словах и символах:

  1. vocabDic: содержит словарь, ключ: слово, значение: словарь с информацией о нем
  2. kanjiDic: содержит кандзи (одиночный японский символ), ключ: кандзи, значение: словарь с информацией о нем

    Теперь я хотел бы пройтись по каждому символу каждого слова в vocabDic и найти этот символ в словаре кандзи. Моя цель - создать CSV-файл, который я затем смогу импортировать в базу данных в виде таблицы соединений для словаря и кандзи.
    Моя версия Python - 2.6.
    Мой код выглядит следующим образом:

    kanjiVocabJoinWriter = csv.writer(open('kanjiVocabJoin.csv', 'wb'), delimiter=',', quotechar='|', quoting=csv.QUOTE_MINIMAL)
    kanjiVocabJoinCount = 1
    
    #loop through dictionary
    for key, val in vocabDic.iteritems():
        if val['lang'] is 'jpn': # only check japanese words
            vocab = val['text']
            print vocab
            # loop through vocab string
            for v in vocab:
                 test = kanjiDic.get(v)
                 print v
                 print test
                 if test is not None:
                    print str(kanjiVocabJoinCount)+','+str(test['id'])+','+str(val['id'])
                    kanjiVocabJoinWriter([str(kanjiVocabJoinCount),str(test['id']),str(val['id'])])
                    kanjiVocabJoinCount = kanjiVocabJoinCount+1
    

Если я печатаю переменные в командной строке, я получаю:
Vocab: работы, печатные издания на японском языке
v (один символ вокаба в цикле for):
тест (персонаж посмотрел в kanjiDic): нет

Мне кажется, что цикл for портит кодировку.
Я пробовал различные функции (декодировать, кодировать ..), но пока не повезло.
Есть идеи о том, как я могу заставить это работать?
Помощь будет очень ценится.

1 Ответ

11 голосов
/ 07 августа 2011

Из вашего описания проблемы это звучит так: vocab - это закодированный объект str, а не объект unicode.

Для конкретности, предположим, что vocab равно u'債務の天井', закодированному вutf-8:

In [42]: v=u'債務の天井'
In [43]: vocab=v.encode('utf-8')   # val['text']
Out[43]: '\xe5\x82\xb5\xe5\x8b\x99\xe3\x81\xae\xe5\xa4\xa9\xe4\xba\x95'

Если вы перебираете закодированный объект str, вы получаете один байт за раз: \xe5, затем \x82, затем \xb5 и т. Д.

Однако, если вы зациклите объект Unicode, вы получите один символ Unicode за раз:

In [45]: for v in u'債務の天井':
   ....:     print(v)    
債
務
の
天
井

Обратите внимание, что первый символ Unicode, закодированный в utf-8, равен 3 байта:

In [49]: u'債'.encode('utf-8')
Out[49]: '\xe5\x82\xb5'

Вот почему при циклическом обходе байтов при печати по одному байту за раз (например, print \xe5) не удается распознать распознаваемый символ.

Похоже, вам нужно декодироватьваши str объекты и работа с unicode объектами.Вы не упомянули, какую кодировку вы используете для своих str объектов.Если это utf-8, то вы бы расшифровали его следующим образом:

vocab=val['text'].decode('utf-8')

Если вы не уверены, в какой кодировке val['text'] находится, опубликуйте вывод

print(repr(vocab))

и, возможно, мы можем угадать кодировку.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...