2009-06-02 79 views
3

目前我有一个用python编写的简单IRC bot。Python IRC bot和编码问题

由于我将它迁移到python 3.0中区分字节和unicode字符串,我开始有编码问题。具体而言,其他人不发送UTF-8。

现在,我可以告诉所有人发送UTF-8(他们应该不管),但更好的解决方案将尝试让Python默认为其他编码或类似。

到目前为止,代码如下所示:

data = str(irc.recv(4096),"UTF-8", "replace") 

至少不会抛出异常。但是,我想要通过它:我想让我的机器人默认为另一种编码,或尝试以某种方式检测“麻烦的字符”。

此外,我需要弄清楚这个mIRC实际使用的神秘编码是什么 - 因为其他客户端似乎能正常工作并发送UTF-8。

我应该如何去做这些事情?

回答

-1

好吧,经过一番调查发现chardet在python 3上遇到了麻烦。事实证明,解决方案比我想象的要简单。如果UTF-8不切割它,我选择回到CP1252上:

data = irc.recv (4096) 
try: data = str(data,"UTF-8") 
except UnicodeDecodeError: data = str(data,"CP1252") 

这似乎是工作。虽然它没有检测到编码,所以如果有人使用既不是UTF-8也不是CP1252的编码,我会再次遇到问题。

这实在只是一个临时解决方案。

+1

cp1252将始终显示为适用于任何非零字节序列,因为它将代码点分配给除零以外的每个字节值。 – RichieHindle 2009-06-02 13:37:01

3

chardet应该有帮助 - 这是用于检测未知编码的规范Python库。

+0

尝试,现在。我会看到它在哪里。 – cwj 2009-06-02 10:57:35

0

作为RichieHindle提到的,chardet可能是您的最佳解决方案。不过,如果你想覆盖文本的约90%,你会看到,你可以使用我用:

def decode(bytes): 
    try: 
     text = bytes.decode('utf-8') 
    except UnicodeDecodeError: 
     try: 
      text = bytes.decode('iso-8859-1') 
     except UnicodeDecodeError: 
      text = bytes.decode('cp1252') 
    return text 


def encode(bytes): 
    try: 
     text = bytes.encode('utf-8') 
    except UnicodeEncodeError: 
     try: 
      text = bytes.encode('iso-8859-1') 
     except UnicodeEncodeError: 
      text = bytes.encode('cp1252') 
    return text 
0

只使用chardet的会导致不良的结果,其中消息很短(这是情况的情况下IRC)。

Chardet结合在整个消息中记住特定用户的编码可能是合理的。但是,为了简单起见,我会使用一些可能的编码(编码取决于文化和时代,请参阅http://en.wikipedia.org/wiki/Internet_Relay_Chat#Character_encoding),如果它们失败,我会去chardet(如果有人使用某些东亚编码,这将帮助我们)。

例如:

def decode_irc(raw, preferred_encs = ["UTF-8", "CP1252", "ISO-8859-1"]): 
    changed = False 
    for enc in preferred_encs: 
     try: 
      res = raw.decode(enc) 
      changed = True 
      break 
     except: 
      pass 
    if not changed: 
     try: 
      enc = chardet.detect(raw)['encoding'] 
      res = raw.decode(enc) 
     except: 
      res = raw.decode(enc, 'ignore') 
return res 
+0

这试图做`res = raw.decode('U')`然后立即放弃。 – 2014-05-02 20:16:38