【问题标题】:Statically copy C-string of variable length静态复制可变长度的 C 字符串
【发布时间】:2021-05-11 00:14:00
【问题描述】:

假设我有函数foo,我希望在其中创建input_str 内容的深层副本并将其存储在指针temp_cpy 中。是否有任何 C 字符串函数可以在不动态分配内存到 temp_cpy 的情况下执行此操作?

void foo(const char *input_str)
{
    char *temp_cpy = NULL;
}

我不想简单地设置temp_cpy = input_str,因为temp_cpy会在函数中被修改,但input_str应该保持不变。

谢谢。

【问题讨论】:

    标签: c copy c-strings


    【解决方案1】:

    必须在某处为字符串副本的内容提供存储空间。没有什么神奇的方法可以复制不需要额外的存储空间。

    然而,这可以在堆栈上,与堆相对,使用 variable-length array

    strlenstrcpy 可用于完成此操作:

    void foo(const char *input_str)
    {
        char temp[strlen(input_str) + 1];
        strcpy(temp, str);
        /* ... */
    }
    

    如果您的平台不支持 VLA,则必须使用堆内存。 strdup 函数通常可用。如果不是,可以使用malloc 轻松复制。完成后一定要记得free这个内存。

    void foo(const char *input_str)
    {
        char *temp = strdup(input_str);
        /* ... */
        free(temp);
    }
    

    void foo(const char *input_str)
    {
        char *temp = malloc(strlen(input_str) + 1);
        strcpy(temp, input_str);
        /* ... */
        free(temp);
    }
    

    如果你的平台不支持 VLA,并且由于某种原因你真的不能使用堆,那么剩下的唯一选择就是一个预定最大长度的缓冲区。这是一种特殊情况,应尽可能避免,因为它会产生您必须跟踪的额外限制。

    #define MAX_FOO_BUFSZ 255
    
    void foo(const char *input_str)
    {                         
        char buffer[MAX_FOO_BUFSZ + 1] = { 0 };
        strncpy(buffer, input_str, MAX_FOO_BUFSZ);    
        
        /* ... */
    } 
    

    【讨论】:

    • 需要注意的是,并非所有编译器都支持 VLA(看你微软)。
    【解决方案2】:

    您也可以使用strdup 函数(它是POSIX,但大多数实现都支持)

    char *foo(const char *input_str)
    {
        char *temp = strdup(input_str);
        if(temp)
        {
            // do some stuff
        }
        return temp;
    }
    

    记得在不需要时释放分配的内存。

    【讨论】:

      猜你喜欢
      • 2011-04-19
      • 2018-03-03
      • 1970-01-01
      • 1970-01-01
      • 2012-10-25
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-10-15
      相关资源
      最近更新 更多