【问题标题】:Safe string copy in C/C++C/C++ 中的安全字符串复制
【发布时间】:2011-07-11 13:00:34
【问题描述】:

我为 C 字符串编写了这个字符串复制例程。它应该表现得像 strlcpy,即 - 如果 size > 0,则 null 终止目标,并返回源字符串的长度。

但是,如果源指针或目标指针为空,我也希望函数失败,并以某种方式通知调用者。但我想不出一种非常优雅的方式来做到这一点。现在我发送两个负值作为大小来表示源或目标指针指向空。因此我将返回类型从 size_t 更改为有符号整数,我对这个接口不满意。什么是更好的界面?

  #include <cstddef> // size_t
  #include <cstdint> // 32 bit int

  const std::int32_t SRC_NULL = -1;
  const std::int32_t DST_NULL = -2;

  std::int32_t CopyStringn (char *dest, const char *src, std::size_t size) {
     const char* temp (src);
     if (temp == NULL)
         return SRC_NULL;
     if (dest == NULL)
         return DST_NULL;
     while (*temp) {
        if (size > 1) {
           *dest++ = *temp;
           --size;
        }
        ++temp;
     }

     if (size)
         *dest = '\0';

     return static_cast<std::int32_t> (temp - src); // Length does not include null
}

【问题讨论】:

  • 如果您使用的是 C++,您有什么特殊原因使用std::string
  • 如果你想要一个魔法值来表示空输入,那么 0 呢?然后返回源字符串长度包括 null 而不是排除它,因此在所有其他情况下它始终至少为 1。两个魔法值似乎有点过头了——调用者真的需要使用这个函数来检查两个指针​​中的哪一个是空的吗?如果真的需要这样的功能,难道不能和这个功能分开吗,它是关于复制字符串的。
  • @dreamlax Ohh.. 我正在使用/修改一些使用大量 c 风格编码的代码,以及 strcpy 和 strtok,因此有时会默默地失败:( 所以我用相对的方法删除了这些函数更安全的。
  • std::string替换可能会更容易,而且更不容易出错。

标签: c++ c string


【解决方案1】:

在 C++ 中,您可以抛出异常。

【讨论】:

    【解决方案2】:

    魔术返回值很少是个好主意。我希望这样的函数可以告诉我将复制多少个字符,这就是应该返回的内容。如果 src 或 dest 为 NULL,则复制 0 个字符,返回 0。

    或者,如果所有内容都已复制并正确以 0 结尾,您可以选择返回 1/true,否则返回 0/false。

    【讨论】:

    • size 不会变为零,因为 size 只会减小它 size > 1.
    • 你说得对,不知道为什么我的大脑坚持说size &gt;= 1。已编辑。
    • “我希望这样的函数能告诉我复制了多少个字符”——这不是 strlcpy 返回的结果,因此可能不是该函数的目标受众所期望的。
    • 好吧,这里真的很晚了(凌晨 3 点)我会把“是”改成“会是”然后睡觉:P
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2017-04-23
    • 1970-01-01
    • 2019-03-18
    • 1970-01-01
    • 1970-01-01
    • 2015-11-03
    • 1970-01-01
    相关资源
    最近更新 更多