【问题标题】:C - Get substring after first n characters of stringC - 在字符串的前 n 个字符之后获取子字符串
【发布时间】:2017-02-09 20:26:39
【问题描述】:

事实证明,要做到这一点非常困难,而且我还没有通过现有问题找到一个直接的解决方案。我查看了几个重复的问题,但它们不是我想要的。

我已经尝试过这样的事情,但我显然误解了 strncpy 的工作原理。我想得到 all 的文本 after 字符串的前 14 个字符。

int length = sizeof(str) - 14;
strncpy(substr, str+14, length);

最简单的方法是什么?

【问题讨论】:

  • 你的意思是int length = strlen(str) - 14;吗?我假设您检查它之前至少有 15 个字符。
  • str的声明是什么?
  • 另外,只使用strcpy 有什么问题? strcpy(substr, str+14);

标签: c string substring c-strings


【解决方案1】:

您是否误解了数学的工作原理? 10 - 14 = -4

编辑:

有一个

char str[10];
int length = sizeof(str) - 14;

插入原始帖子。 (查看编辑

此外,您不应使用sizeof 来计算字符串的长度,而应使用strlen()sizeof 运算符用于找出类型的大小,假设str 是数组或指针sizeof 将返回第一种情况下的元素个数和相当于sizeof(void *) 的指针大小在第二个。

字符串是一个数组,但是这个数组的大小不是字符串的长度,一个10个字符的字符串可以存入一个100个元素的数组,所以问题不是strncpy(你应该避免顺便说一句,因为它不能保证nul 终止),真正的问题是你如何处理它。

假设你有一个长度≥14的有效字符串,那么

strcpy(substr, str + 14)

应该够了!

您当然应该确保目标数组substr 足够大,并且str 的长度大于或等于14,或者,您可以在这两种情况下调用未定义的行为。

如果你之前知道str的长度那么,你可以试试

memcpy(substr, str + 14, length_str - 14);
substr[length_str - 14] = '\0';

注意substr 必须至少有nul 终止符的length_str - 14 元素+1,并且如果您知道str 中有一个'\0' 终止符,那么

// Leaving + 1 explicitly to denote the '\0'
memcpy(substr, str + 14, length_str - 14 + 1);

应该在一次调用中复制它。

【讨论】:

    【解决方案2】:

    我已经尝试过这样的事情,但我显然误解了如何 strncpy 有效。我想获得前 14 个之后的所有文本 字符串的字符。

    int length = strlen(str) - 14;
    if(length >= 0) {
       strncpy(substr, str+13, length);
       substr[length] = '\0';
    }
    

    【讨论】:

    • @IharobAlAsimi,感谢您的建议。我已经编辑了答案。
    • 上面的代码没有达到既定的目标:我想得到所有的文本之后字符串的前14个字符。它无缘无故使用strncpy()。等价于strcpy(substr, str+13);,更简单更易读,但仍然是偏移量错误。
    • @chqrlie,您可能想在 OP 问题的字里行间阅读。目标不仅是实现目标,而且还要加深对我的回答试图提供的strncpy 的理解。
    • 为此,您需要编写 strncpy(substr, str+14, length);,但它不会教给 OP 关于 strncpy() 的任何内容,因为对于这些参数,memcpy() 会更合适。所有 OP 需要了解的关于 strncpy 的信息都在这里:randomascii.wordpress.com/2013/04/03/stop-using-strncpy-already 和这里:blog.liw.fi/posts/strncpy
    • 顺便说一句,不需要在字里行间阅读:我显然误解了strncpy 的工作原理 非常清楚!我对strncpy 的建议同样明确:不要使用它!。阅读文章以了解原因。
    【解决方案3】:

    您的尝试有两个问题:

    • sizeof(str) 不计算str 指向的字符串中的字符数。它评估为str 的大小,它可以是指针或数组,因为您没有发布定义。为此,您应该使用strlen(str)

    • strncpy() 不会像你认为的那样做。这个函数很容易出错。它永远不是任何工作的正确工具,不要使用它。

    解决方案很简单:如果您知道str 至少有 14 个字符,并且substr 指向一个足够长的数组以接收字符串的其余部分,那么只需这样写:

    strcpy(substr, str + 14);  // copy all characters, skipping the first 14 bytes
    

    如果str 可能少于 14 个字符,请添加测试:

    *substr = '\0';
    if (strlen(str) >= 14) {
        strcpy(substr, str + 14);
    }
    

    如果您知道目标的大小,但不知道它是否足够大以接收字符串的其余部分,请使用:

    *substr = '\0';
    if (strlen(str) >= 14) {
        snprintf(substr, substr_size, "%s", str + 14);
    }
    

    或者这个替代方案:

    *substr = '\0';
    if (strlen(str) >= 14) {
        // copy at most substr_size-1 characters from str, skipping the first 14 bytes.
        // and null terminate the destination string.
        strncat(substr, substr_size - 1, str + 14);
    }
    

    【讨论】:

      猜你喜欢
      • 2013-02-07
      • 1970-01-01
      • 1970-01-01
      • 2012-01-14
      • 2022-11-10
      • 2015-06-06
      • 2010-12-28
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多