C++使用SAPI实现TTS时字符串参数调用Speak函数失败求助
解决SAPI文本转语音函数
ISpVoice::Speak的参数类型不兼容问题 核心问题是**ISpVoice::Speak的第一个参数要求宽字符指针(LPCWSTR)**,而你传入的std::string是窄字符类型,类型不匹配导致代码无法编译或运行。你之前尝试的L + text是错误语法(L只能用于字符串字面量前缀),直接传递std::string对象同样不满足参数要求。
方案1:改用宽字符串参数(推荐)
直接将函数参数改为std::wstring,调用时使用宽字符串字面量(前缀L):
#include <iostream> #include <sapi.h> #include <string> using namespace std; void bot(wstring text) { ISpVoice* pVoice = NULL; if (FAILED(::CoInitialize(NULL))) { exit(1); } HRESULT hr = CoCreateInstance(CLSID_SpVoice, NULL, CLSCTX_ALL, IID_ISpVoice, (void**)&pVoice); if (SUCCEEDED(hr)) { // 调用c_str()获取LPCWSTR类型的宽字符指针 hr = pVoice->Speak(text.c_str(), 0, NULL); pVoice->Release(); pVoice = NULL; } ::CoUninitialize(); } int main() { bot(L"Hello"); bot(L"Hi, my name is blah blah"); return 0; }
方案2:保留窄字符串参数,添加类型转换
如果需要继续使用std::string作为参数,需要将窄字符串转换为宽字符串,可借助Windows API实现转换:
#include <iostream> #include <sapi.h> #include <string> #include <windows.h> using namespace std; // 窄字符串转宽字符串(UTF-8编码) wstring string_to_wstring(const string& str) { int wide_size = MultiByteToWideChar(CP_UTF8, 0, str.c_str(), (int)str.size(), NULL, 0); wstring wide_str(wide_size, 0); MultiByteToWideChar(CP_UTF8, 0, str.c_str(), (int)str.size(), &wide_str[0], wide_size); return wide_str; } void bot(string text) { ISpVoice* pVoice = NULL; if (FAILED(::CoInitialize(NULL))) { exit(1); } HRESULT hr = CoCreateInstance(CLSID_SpVoice, NULL, CLSCTX_ALL, IID_ISpVoice, (void**)&pVoice); if (SUCCEEDED(hr)) { wstring wide_text = string_to_wstring(text); hr = pVoice->Speak(wide_text.c_str(), 0, NULL); pVoice->Release(); pVoice = NULL; } ::CoUninitialize(); } int main() { bot("Hello"); bot("Hi, my name is blah blah"); return 0; }
额外注意事项
- 编译时必须链接SAPI库:在Visual Studio中,需在项目属性的链接器 -> 输入 -> 附加依赖项中添加
sapi.lib,否则会出现未定义符号的链接错误。 - 更规范的做法是将
CoInitialize放在程序入口(main开头)调用一次,CoUninitialize放在程序退出前调用一次,避免每次调用bot函数重复初始化/释放COM环境。
内容的提问来源于stack exchange,提问作者MaxMouse
相关产品推荐
相关产品推荐

