如何在不使用malloc()的情况下创建子字符串

时间:2012-12-28 07:58:29

标签: c malloc free

如何实现一个子字符串函数,如下面的函数返回子字符串,但不在进程中使用malloc(),所以我不必担心使用{{{ 1}}功能。这甚至可能吗?

free()

更新时间:2012年12月30日

考虑了所有的答案和评论后,很明显基本上我正在尝试做的是创建一个动态大小的数组(即子字符串),这在C中是不可能的,没有某些地方必须使用某种类型的const char *substring(const char *string, int position, int length) { char *pointer; int c; pointer = malloc(length+1); if (pointer == NULL) { printf("Unable to allocate memory.\n"); exit(EXIT_FAILURE); } for (c = 0 ; c < position -1 ; c++) string++; for (c = 0 ; c < length ; c++) { *(pointer+c) = *string; string++; } *(pointer+c) = '\0'; return substr; } 函数和后续malloc()调用子字符串指针或没有垃圾收集器的帮助。我试图整合free()垃圾收集器,正如@elhadi所建议,但到目前为止not been able to get this to work in my Xcode project。所以我选择在libgcmalloc()上使用以下代码。

free()

5 个答案:

答案 0 :(得分:6)

我看到两个选项:

如果你可以销毁源字符串(通常是坏事):

{
    string[ position + length] = 0;
    return & string[ position ];
}

注意:(请参阅Cole Johnsons注意:免费不再适用于返回的指针!)

如果无法修改源字符串: 修改您的方法签名,以便调用者必须担心它:

const char *substring(const char *source, char* destination, int position, int length)

将修改后的字符串放入目的地(并将其返回)。

甚至不考虑这个:

const char *substring(const char *string, int position, int length)
{
    char *pointer;
    int c;
    static char modifiedString[256];
 ...
    return modifiedString;
}

在函数内部使用静态变量来修改结果... (这不是线程安全的(不可重入!))

答案 1 :(得分:2)

const char *substring(const char *string, char *substr, int position, int length)
{
    int c;

    for (c = 0 ; c < position -1 ; c++)
        string++;

    for (c = 0 ; c < length ; c++)
    {
        *(substr+c) = *string;
        string++;
    }

    *(substr+c) = '\0';

    return substr;
}

调用函数......

int main(int argc, char * argv[]) {
    char substr[10];

    substring("hello! World", &substr[0], 2, 4);
}

答案 2 :(得分:2)

使用本地缓冲区(自动数组)和这样的函数:

void substr(char *dst, const char *src, size_t loc, size_t len)
{
    memcpy(dst, src + loc, len);
    dst[len] = 0;
}

这样称呼:

const size_t size = 3;
char buf[size + 1]; // this is an auto array, it will be "freed" at the end of the scope
substr(buf, "abcdFOObar", 4, size);

始终确保缓冲区长度至少为len + 1个字节,以避免缓冲区溢出错误。

答案 3 :(得分:1)

最好的方法是:

typedef struct vstr_t {
     char *s;
     int   len;
} vstr_t;

#define vstr_set(d, l)                  \
    ({                                  \
        vstr_t vs = {.s = d, .len = l}; \
                                        \
        vs;                             \
    })

#define vstr_fmt_arg(vs) (vs).len, (vs).s

int main()
{    
    const char *message = "hello universe";

    printf( "substring: [%.*s]\n", vstr_fmt_arg(vstr_set(smpl + 6, 8)));

    return 0;
}

答案 4 :(得分:0)

你可以使用垃圾收集器,你第一次分配内存,垃圾收集器会在不需要时释放内存。
你应该包括

#include "gc.h"

在主要内容你应该做类似的事情

GC_INIT();  /* Optional on Linux/X86;*/

你的substr函数是:

char *substr(const char* buffer, const int offset, int len)
{
    char sub = (char*)GC_MALLOC(len+1);
    memcpy(sub, buffer + offset, len);
    sub[len] = 0;
    return sub;
}

您应该与libgc.a

相关联