使用wcscpy_s
和使用wcsncpy
之间是否存在实际差异?唯一的区别似乎是参数和返回值的顺序:
errno_t wcscpy_s(wchar_t *strDestination,
size_t numberOfElements,
const wchar_t *strSource);
wchar_t *wcsncpy(wchar_t *strDest,
const wchar_t *strSource,
size_t count );
如果没有实际差异,为什么Microsoft需要将wcscpy_s
添加到Visual Studio,wcsncpy
已经可用且标准功能?
从Visual Studio移植到gcc时,将wcscpy_s
替换为wcsncpy
是否可以?
答案 0 :(得分:9)
这两个功能没有相同的行为。
来自the MSDN documentation of wcscpy_s
:
成功执行后,目标字符串将始终为空终止。
根据wcsncpy
的规范(C11 7.29.4.2.2 / 1-3):
#include <wchar.h> wchar_t *wcsncpy(wchar_t * restrict s1, const wchar_t * restrict s2, size_t n);
wcsncpy
函数复制不超过n
个宽字符(跟随空的字符) 从s2
指向的数组到指向的数组,不会复制宽字符s1
。如果
s2
指向的数组是一个短于n
个宽字符的宽字符串,则空宽字符将附加到s1
指向的数组中的副本,直到n
全部字符都已写入
和脚注(#346):
因此,如果
n
指向的数组的第一个s2
宽字符中没有空宽字符,则结果将不会以空值终止。
请注意,strncpy
和wcsncpy
不适用于以null结尾的字符串。它们设计用于零填充,固定宽度的字符串。
答案 1 :(得分:5)
另一个区别(只花了我几个小时盯着代码,想知道发生了什么)是wcscpy_s函数默认情况下会在你超出缓冲区时终止应用程序。
我预计它的行为就像一个strncpy变种。事实并非如此!
您可以使用_set_invalid_parameter_handler函数显然更改此行为。
答案 2 :(得分:1)
wcscpy_s
is more secure,它可以检测到您的错误并触发Invalid Parameter Handler Routine。为了在不导致崩溃的情况下处理此类错误,他们提供了_set_invalid_parameter_handler
。
答案 3 :(得分:0)
附加_s的函数是更安全的函数。通常,例如,VS2012将不标记尾随_s的函数标记为“已弃用”。你会收到警告。有关其他信息:MSDN有大量有关此信息。