You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何将char*转为wchar_t*并在Python中正确显示宽字符串?

解决方案:还原UTF-16LE格式的宽字符串

你的核心问题是:EP_ProtectedStringByID返回的是UTF-16LE编码的字节序列(ASCII字符后跟0字节是小端UTF-16的典型特征),而mbstowcs是用来将多字节字符串(如UTF-8)转换为宽字符的工具,完全不适用这种场景,才会出现遇\0截断的问题。下面提供两种可行方案:

方法一:Python层直接解码(简单高效)

既然buf_string_2本身是bytes类型,直接用Python原生的编码解码功能处理即可,无需C层转换:

# 截取有效长度的字节后,用utf-16-le解码
target_str = buf_string_2[:buf_size].decode('utf-16-le')
print(target_str)

方法二:Cython层正确处理宽字符

如果必须在Cython逻辑内完成转换,直接将char*强制转为wchar_t*(Windows平台下wchar_t默认就是UTF-16LE),再调用Python的宽字符转字符串接口:

cdef extern from "Python.h":
    object PyUnicode_FromWideChar(const wchar_t* w, Py_ssize_t size)

if EP_ProtectedStringByID(2, buf_string_2, buf_size) != 0:
    # 直接强制转换字节序列为宽字符指针
    cdef wchar_t* wide_buf = <wchar_t*>buf_string_2
    # 计算宽字符数量:总字节数除以单个宽字符的字节数
    cdef Py_ssize_t wide_len = buf_size // sizeof(wchar_t)
    pystr_2 = PyUnicode_FromWideChar(wide_buf, wide_len)
    wide_string = str(pystr_2)
    print('WideString :', wide_string)

关键说明

  • 原始输出的字节序列中,ASCII字符以字符码+0的形式存储,这是UTF-16LE(小端字节序UTF-16)的标准格式。
  • mbstowcs的设计逻辑是处理以\0结尾的多字节字符串,所以遇到第一个\0就会停止转换,完全不适合处理宽字节序列。
  • 解码时务必截取buf_size长度的字节,避免包含内存中多余的无效内容。

内容的提问来源于stack exchange,提问作者MelectronVolt

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.26 19:13:39