如何正确解码Unicode?WiFi SSID特殊字符解码问题求助
解决WiFi SSID特殊字符解码问题
你的问题出在iw scan输出的SSID特殊字符是以十六进制转义序列(比如\xc3\xb6)的形式呈现的,直接用utf-8解码stdout会把这些转义序列当成普通文本字符串,而不是解析为对应的字符。以下是具体的修复方案:
修复后的代码
import subprocess import re import codecs def get_ssid_list(): '''获取可用SSID列表,使用Unix工具iw。返回填充后的列表''' result = subprocess.run(["iw", WLAN_ITF, "scan"], capture_output=True) iwlist_result = result.stdout.decode("utf-8") # 修正正则:匹配带引号的SSID内容,避免捕获多余字符 ssid_regexp = re.compile(r'SSID: "(.*)"\n', re.MULTILINE) ssid_list = list(set(ssid_regexp.findall(iwlist_result))) # 处理转义序列并过滤无效SSID def fix_ssid(ssid): try: # 将转义的十六进制字符串解码为原始字节,再转为UTF-8字符串 decoded_bytes, _ = codecs.escape_decode(ssid.encode('utf-8')) return decoded_bytes.decode('utf-8') except: # 解码失败时返回原始SSID,避免崩溃 return ssid ssid_list = [fix_ssid(ssid) for ssid in ssid_list if '\x00' not in ssid and ssid.strip()] if not ssid_list: return None else: ssid_list.sort(key=str.lower) return ssid_list
关键修复点
正则表达式优化:
原来的正则SSID: (.*)\n会捕获到SSID前后的引号(如果iw输出带引号的话),修正后的SSID: "(.*)"\n直接提取引号内的真实SSID内容。通用转义处理:
使用codecs.escape_decode()替代手动替换:- 它能自动识别所有类似
\xXX的十六进制转义序列,将其转换为对应的字节。 - 再通过
utf-8解码就能得到正确的特殊字符(比如\xc3\xb6转为ö)。
- 它能自动识别所有类似
异常安全:
添加异常捕获,确保遇到格式异常的SSID时不会导致函数崩溃,而是返回原始值。
为什么之前的方法无效?
你之前手动替换\x20为空格的方式只能处理单一情况,无法覆盖所有特殊字符的转义序列。而escape_decode是通用的转义解码工具,能处理所有符合\xXX格式的转义字符。
内容的提问来源于stack exchange,提问作者Piocky
相关产品推荐
相关产品推荐

