我正在使用L"79349 Dexter 03 05"格式编写一个简单的序列化

(假设Dexter部分始终为1个字。)

该字符串将被读入3个int和一个wchar_t数组

我目前有以下代码:

#include <iostream>
#include <stdio.h>
#include <string>

using namespace std;

int main()
{
    int id=-1,season=-1,episode=-1;
    wchar_t name[128];
    swscanf_s(L"79349 Dexter 03 05", L"%d %ls %d %d", &id, name, &season, &episode);

    wcout << "id is " << id << endl;
    wcout << "name is " << wstring(name) << endl; //wprintf(L"name is %ls",name);
    wcout << "season is " << season << endl;
    wcout << "episode is " << episode << endl;
}

上面的代码已编译(在VS '13中),没有问题,但是在执行时会崩溃。使用调试选项,我收到消息:Unhandled exception at 0xFEFEFEFE in test3.exe: 0xC0000005: Access violation executing location 0xFEFEFEFE.
通过省略某些部分,我发现在阅读name时会发生此问题。

例如,以下工作正常:
swscanf_s(L"79349 Dexter 03 05", L"%d %*ls %d %d", &id, &season, &episode);

我究竟做错了什么?

我的猜测是我缺少一些简单而琐碎的东西,但我自己却找不到。提前致谢。

最佳答案

我的声誉目前很少有人评论。正如Brett所说,您需要使用wcstok_s。您想要做的是将长字符串“标记”为较小的标记字符串。这就是wcstok_s会为您做的。另一方面,swscanf_s将尝试将您传递的整个字符串转换为第一个format参数。

这对您不起作用的另一个原因是,您尚未指定要扫描的字节数。 “_s”版本更“安全”,因为它们可以防止缓冲区溢出,这会损坏内存并引起各种问题。如果您更换:

swscanf_s(L".IHATECPP.",L".%ls.",name);


swscanf_s(L".IHATECPP.", L".%ls.", name, _countof(name));

结果将是:IHATECPP.。首先 ”。” (点)未解析。

这个问题:如果可以使用更多的C++风格的例程而不是较早的C风格的例程,Split a string in C++?可能会对您有所帮助。如果您由于某种原因而无法这样做,那么:C++ Split Wide Char String可能会为您提供一些想法,因为它使用的是wcstok()。一旦wcstok_s将原始字符串拆分为较小的子字符串( token ),则需要将已知的字符串转换为整数。

通常,您可以搜索“C++标记化”,并且应该找到很多示例。

10-08 00:24