Python - 编码器编码ascii到unicode:错误

时间:2010-02-15 10:31:16

标签: python transliteration

:)我正在尝试将输入文件(目前在英语中)的音译反转回其原始形式(在印地语中)

输入文件的示例或部分内容如下所示:

E-k- b-u-d-z*dhi-m-aan- p-ksii#

E-k- ghn-e- j-ngg-l- m-e-ng E-k- b-h-u-t- UUNNc-aa p-e-dr thaa#
U-s- k-ii p-t-z*t-o-ng s-e- l-d-ii shaakhaay-e-ng m-j-*zb-uut- b-aaj-u-O-ng k-ii t-r-h- pheil-ii h-u-II thiing#
w-n- h-NNs-o-ng k-aa E-k- jhu-nhz*D- I-s- p-e-dr p-r- n-i-w-aas- k-r-t-aa thaa#
w-e- s-b- y-h-aaNN s-u-r-ksi-t- the- AUr- b-dre- AAr-aam- s-e- r-h-t-e- the-#
U-n- m-e-ng s-e- E-k- p-ksii b-h-u-t- b-u-d-z*dhi-m-aan- thaa#
I-s- b-u-d-z*dhi-m-aan- p-ksii n-e- E-k- d-i-n- p-e-dr k-ii j-dr m-e-ng s-e- E-k- l-t-aa k-o- U-g-t-e- d-e-khaa# 
I-s- k-e- b-aar-e- m-e-ng U-s-n-e- d-uus-r-e- p-ksi-y-o-ng s-e- b-aat- k-ii#
"k-z*y-aa t-u-m-z*h-e-ng w-h- l-t-aa d-i-khaaII d-e-t-ii h-ei", U-s- n-e- U-n- s-e- p-uuchaa "t-u-m-z*h-e-ng I-s-e- n-Shz*T- k-r- d-e-n-aa c-aah-i-E-"#
"I-s-e- k-z*y-o-ng n-Shz*T- k-r- d-e-n-aa c-aah-i-E-?" h-NNs-o-ng n-e- AAshz*c-*ry- s-e- p-uuchaa "y-h- t-o- I-t-n-ii cho-T-ii s-e- h-ei#
h-m-e-ng y-h- k-z*y-aa h-aan-i- p-h-u-NNc-aa s-k-t-ii h-ei"#
"m-e-r-e- m-i-tro-ng," b-u-d-z*dhi-m-aan- p-ksii n-e- U-t-z*t-r- d-i-y-aa "w-h- cho-T-ii s-ii l-t-aa j-l-z*d-ii h-ii b-drii h-o- j-aay-e-g-ii#
y-h- h-m-aar-e- p-e-dr p-r- c-Dh*z k-r- U-s- s-e- l-i-p-T-t-ii j-aay-e-g-ii AUr- phi-r- m-o-T-ii AUr- m-j-*zb-uut- h-o- j-aay-e-g-ii"#
"t-o- k-z*y-aa h-u-AA"#

它在英语中的等同含义是:

A WISE OLD BIRD.

Deep in the forest stood a very tall tree.
Its leafy branches spread out like long arms.
This was the home of a flock of wild geese.
They were safe there.
One of the geese was a wild old bird.
One  day this wise old bird noticed  a small creeper growing at the foot of the tree.
He spoke to the other birds about it.
"Do you see that creeper ?" he said to them.
"You must destroy it."
"Why must we destroy it ?" asked the geese in surprise.
"It is so small.
What harm can it do?"
"My friends," replied the wise old bird, " that little creeper will soon grow.

我的脚本如下所示:

#!/usr/bin/python
# -*- coding: UTF-8 -*-
import sys
CODEC = 'utf-8'
input_file=sys.argv[1]
output_file=sys.argv[2]
list1=[]



f=open(input_file,'r')
f1 = open(output_file,'w')

english_hindi_dict={'A' : u'अ' ,  'AA' : u'आ ' , 'I' : u'इ' , 'II' : u'ई ' , 'U' : u'उ ' ,\
                'UU' : u'ऊ' , 'r' : u'ऋ' , 'E' : u'ए' , 'ai' : u'ऐ' , 'O' : u'ओ' , 'AU' : u'औ' ,\
                'k' : u'क' , 'kh' : u'ख' , 'g' : u'ग' , 'gh' : u'घ' , 'c' : u'च' , 'ch' : u'छ',\
                'j': u'ज' , 'jh' : u'झ' , 'tr' : u'त्र' , 'T' : u'ट'  , 'Th' : u'ठ' , 'D' : u'ड',\
                'dr' : u'ड' , 'Dh' : u'ढ' , 'Na' : u'ण' , 'th' : u'त' ,  'tha' : u'थ',\
                'd' : u'द' , 'dh': u'ध' , 'n' : u'न' , 'p' : u'प' , 'ph' : u'फ' ,\
                'b' : u'ब' , 'bh' : u'भ' , 'm' : u'म' , 'y' : u'य' , 'r' : u'र' , 'l' : u'ल' ,\
                'w' : u'व' , 'sh' : u'श' , 'sha' : u'ष', 's' : u'स' , 'h' : u'ह' , 'ks' : u'क्ष' ,\
                'i' : u'ि' , 'ii' : u'ी' , 'u' : u'ु' , 'uu' : u'ू' , 'e' : u'े' ,\
                'aa' : u'ै' , 'o' : u'ो' , 'AU' : u'ौ' ,'H' : u'्' ,'mn' : u'ं' ,\
                'NN' : u'ँ' , 'AW' : u'ॅ' , 'rr' : u'ृ' , '4' : u'४' , '6': u'६'  , '8' : u'८',\
                '2' : u'२' , '5' : u'५' , '3' : u'३' , '7' : u'७' , '9' : u'९' , '1' : u'१'}
for line in f:
      #line=line.strip() to remove a line from its newline character....  
      #line=line.rstrip('.')   
      line=line.replace('-','')
      line=line.replace('#','|') # i am using the or symbol for poornviram
      #line=line.replace('।','')
      #line = line.lower()
for word in line:
    for ch in word:
        if (ch in english_hindi_dict) :
            translatedToken = english_hindi_dict[ch]
        else :
                translatedToken = ch

#{ translatedToken = english_hindi_dict[ch] }

#for ch in line:
    f1.write(translatedToken)
    #print translatedToken
    #line = line.replace( char,english_hindi_dict[char] )   
      #list1.append(line)
f.close()

f1.write(' '.join(list1))

f1.close()

我得到的错误是:

python transliterate_eh_nw.py Hstory.txt op1.txt
Traceback (most recent call last):
  File "transliterate_eh_nw.py", line 43, in <module>
    f1.write(translatedToken)
UnicodeEncodeError: 'ascii' codec can't encode character u'\u092f' in position 0: ordinal not in range(128)

您能否告诉我如何处理此错误。 谢谢.. :))

3 个答案:

答案 0 :(得分:4)

除了你提出的问题之外,你还有一些问题。

(1)概念性问题:“E-k-b-u-d-z * dhi-m-aan-p-ksii#”“english”。它是使用一些罗马化方案用ASCII编写的印地语。它看起来像ITRAN,但ITRAN没有AA和A,它只有aa和a。该计划有名称吗?你能提供一个URL吗?您的对象更好地描述为“将一些印地语文本从未命名的罗马化文本翻译成梵文剧本”。

(2)显示将您的文本从印地语翻译成英语(“A WISE OLD BIRD”等)的结果只是中等有用。预期的梵文输出会更好。

(3)正如@ kaiser.se所说,音译字典有多字节(最多3个字节!)键,其中一些是其他字符的前缀。据推测,AA必须优先A才能识别,gh必须在g之前识别,等等。对词典项目的迭代按照可预测的顺序进行为了您的目的应该被认为是随机的。在随后的代码中,我优先考虑更长的“键”。

(4)字典缺少一些字母键(S t z)或音译规则比我们迄今为止猜测的更复杂

(5)字符#*和 - 的含义并非100%明显。从输入文本中可以看出,z和*仅作为z *

组合出现

(6)如果你解释了例如对...的解释,那将是一个好主意。 shaakhaay-e-ng ...是从sh开始,然后是aa还是从sha开始,然后是a?规则是什么?

您询问的问题的答案当然是其他几个人指出您需要使用显示设备支持的编码对您的unicode输出进行编码,例如: UTF-8。

以下是一些代码:

#!/usr/bin/python
# -*- coding: UTF-8 -*-

input_data = """
E-k- b-u-d-z*dhi-m-aan- p-ksii#

E-k- ghn-e- j-ngg-l- m-e-ng E-k- b-h-u-t- UUNNc-aa p-e-dr thaa#
[snip]
"t-o- k-z*y-aa h-u-AA"#
"""

roman_devanagari_dict={'A' : u'अ' ,  'AA' : u'आ ' , 'I' : u'इ' , 'II' : u'ई ' , 'U' : u'उ ' ,\
[snip]
            '2' : u'२' , '5' : u'५' , '3' : u'३' , '7' : u'७' , '9' : u'९' , '1' : u'१'}

#Presuming we need to do the 3-letter cases then the 2-letter then the 1-letter
replacements = [(-len(k), unicode(k), v) for k, v in roman_devanagari_dict.items()]
replacements.sort()

data = input_data.decode('ascii')

for _junk, from_text, to_text in replacements:
    data = data.replace(from_text, to_text)

# Presuming the '-' are inter-character markers, delete them last, not first
data = data.replace(u'-', '')
data = data.replace(u'#', '')
print "untransliterated:", set(c for c in data if 0x20 < ord(c) < 0x7f)

BOM = u'\ufeff'
outf = open('devanagari.txt', 'w')
outf.write(BOM.encode('utf8')) # for the benefit of clueless Windows s/w
outf.write(data.encode('utf8'))
outf.close()

输出:

एकबुदz *धिमैनपक्षी

更多信息 उसकीपTZ 吨ोनगसेलदीष一个खैयेनगमजžबू吨बैजुओनगकी吨रहफेिलीहुईतीनग वनहँसोनगकैैकझुनहz डइसपडडपरैथथथ वेसेयहैँसेरक्षिtतेौरबडेआआेेेेेेेेेेेेेेेेेे उनमेनगसेएकपक्षीबहुtबुदz धिमैनथa इसबुदžधिमैनपक्षीनेएकदिनपेडकीजडमेनगसेएकल吨ैकोउग吨ेदेखै 更多信息和更多信息,请访问我们的网站 “कžयै吨ुमžहेनगवहल吨ैदिखैईदे吨ीहेि”,उसनेउनसेपूछै “吨ुमžहेनगइसेन小号हžटकरदेनैचैहिए” “这是什么?योनगनSहz टकरदेनैैहिए?” हँसोनगनेआशZ रयसेपूछै“यहtіइtनोछोटीसेहेि हमेनगयहकz यैहैनिपहुँचैसकtहेि“ “मेरेमित्रोनग,” बुदžधिमैनपक्षीनेउTZ 吨रदियै“वहछोटीसील吨ैजलžदीहीबडीहोजैयेगी यहहमैरेपेडपरचढžकरउससेलिपट吨ीजैयेगीौरफिरमोटीौरमजžबू吨होजैयेगी” “tोकz यैहुआ”

在推翻Google翻译时只有几个可识别的单词。

在仔细检查音译表之后

更新

  • 其中三个条目(AA,II和U)在天城座之后有一个空格。也许应该删除空格。

  • 辅音的一般模式似乎是:

DEVANAGARI LETTER XA由x
表示 DEVANAGARI信函XXA由X
表示 DEVANAGARI LETTER XHA由xh
代表 DEVANAGARI LETTER XXHA由Xh代表

然而,3个条目打破了这种模式:
SSA - &gt;但是模式说S
TA - &gt;但是模式说t THA - &gt;但是模式说明了

注意:更改上述3个条目会阻止我的代码抱怨在翻译示例文本时S和t保持不变,并删除了看似异常的sha和tha条目。

  • 条目(D和dr)映射到相同的字符DEVANAGARI LETTER DDA。 D是该角色的预期条目;也许博士应该映射到其他地方。

  • DEVANAGARI LETTER NGA(U + 0919)没有条目;也许它应该被编码为ng - 在示例文本中有一些以ng结尾的单词。

  • 示例文本中未展开的“z *”是否与DEVANAGARI LETTER ZA(U + 095B)有关?

答案 1 :(得分:1)

  

f1.write(''。join(list1))

此时,

list1包含Unicode字符串。您不能将Unicode直接写入文件,它是一个字节接口。您应该显式地对其进行编码(' '.join(list1).encode('utf-8')),或者,正如Ignacio建议的那样,使用codecs包装器隐式编码您发送给它的Unicode字符串。目前,您正在定义变量CODEC,但没有对其进行任何操作。

答案 2 :(得分:1)

您确定要删除所有连字符( - )吗?查看输入文件,看起来所有替换都是两个或三个字符的代码,例如u'I - ':u'इ'。如果是这样,您可以执行类似下面的操作,但请确保您在字典中为所有键和值使用Unicode字符串:

import codecs

# read the whole file at once
f = codecs.open(input_file,'r','ascii')
data = f.read()
f.close()

# perform all the replacements
for k,v in english_hindi_dict.items():
    data = data.replace(k,v)

# write the whole file result
f = codecs.open(output_file,'w',CODEC)
f.write(data)
f.close()

遵循该理论,我得到了以下结果,看起来字典中缺少诸如'z *','t - ','ng'和'ei'之类的翻译。我不读印地语,但谷歌翻译在你的翻译中提出了一些英文单词,所以我认为我走在正确的轨道上。

-z*धिमैन पक्षी

एक घने जngगल मेng एक बहुt- ऊँचै पेड तै
उस की पt-z*t-ोng से लदी शैखैयेng मज*zबूt- बैजुओng की t-रह फeiली हुई तीng
वन हँसोng कै एक झुnhz*ड इस पेड पर निवैस करt-ै तै
वे सब यहैँ सुरक्षिt- ते ौर बडे आरैम से रहt-े ते
उन मेng से एक पक्षी बहुt- बुदz*धिमैन तै
इस बुदz*धिमैन पक्षी ने एक दिन पेड की जड मेng से एक लt-ै को उगt-े देखै 
इस के बैरे मेng उसने दूसरे पक्षियोng से बैt- की
"कz*यै t-ुमz*हेng वह लt-ै दिखैई देt-ी हei", उस ने उन से पूछै "t-ुमz*हेng इसे नShz*ट कर देनै चैहिए"
"इसे कz*योng नShz*ट कर देनै चैहिए?" हँसोng ने आशz*च*rय से पूछै "यह t-ो इt-नी छोटी से हei
हमेng यह कz*यै हैनि पहुँचै सकt-ी हei"
"मेरे मित्रोng," बुदz*धिमैन पक्षी ने उt-z*t-र दियै "वह छोटी सी लt-ै जलz*दी ही बडी हो जैयेगी
यह हमैरे पेड पर चढ*z कर उस से लिपटt-ी जैयेगी ौर फिर मोटी ौर मज*zबूt- हो जैयेगी"
"t-ो कz*यै हुआ"