返回char[]以在strtok()函数中使用它

返回char[]以在strtok()函数中使用它,c,C,我有功能 char *priq_pop(pri_queue q, int *pri) { char *out; if (q->n == 1) return 0; q_elem_t *b = q->buf; out = b[1].data; if (pri) *pri = b[1].pri; /* pull last item to top, then down heap. */ --q->n; int n

我有功能

char *priq_pop(pri_queue q, int *pri)
{
    char *out;
    if (q->n == 1) return 0;

    q_elem_t *b = q->buf;

    out = b[1].data;
    if (pri) *pri = b[1].pri;

    /* pull last item to top, then down heap. */
    --q->n;

    int n = 1, m;
    while ((m = n * 2) < q->n) 
    {
        if (m + 1 < q->n && b[m].pri > b[m + 1].pri)
        {
            m++;
        }

        if (b[q->n].pri <= b[m].pri)
        {
            break;
        }
        b[n] = b[m];
        n = m;
    }

    b[n] = b[q->n];
    if (q->n < q->alloc / 2 && q->n >= 16)
    q->buf = realloc(q->buf, (q->alloc /= 2) * sizeof(b[0]));

    return (char *)out;
}

但是有了这段代码,我的程序在到达
x=strtok(ret,“,”)时停止工作。返回值中存在错误(在
ret
中),因为如果我使用变量
test
,它就是工作。如何解决我的问题?

您正在将常量字符串文本推送到您的队列中:

priq_push(qq, "test2", 2);
priq_push(qq, "test,s", 0);
“test2”
“test,s”
是字符串文本,您正在将指向它们的指针推送到优先级队列中。字符串文字不可写

当您从优先级队列中弹出时,您将得到与您按下的指针相同的指针,然后将其交给
strtok
strtok
需要修改传递的字符串。但是,因为您要向它传递一个指向字符串文字的指针,所以会导致异常

您需要将可写字符串传递给
strtok
。这需要在将其推送到队列之前制作副本(处理完后释放),或者在将其从队列中弹出时制作副本(处理完后再次释放)


您可以使用
strlen
malloc
strcpy
制作可写副本,也可以使用常用(但非标准)的
strdup
。要求人们发现代码中的错误并不特别有效。您应该使用调试器(或添加打印语句)来隔离问题,方法是跟踪程序的进度,并将其与预期发生的情况进行比较。一旦这两个问题出现分歧,你就发现了问题所在。(然后,如果需要,您应该构造一个。)无需强制转换
priq_pop
@OliCharlesworth的返回值,我知道错误在哪里,但我不知道如何修复它。几天前我开始使用C,但我还不明白如何使用指针。我试着自己解决这个问题,但程序没有出现任何错误,所以我没有成功。好的。告诉我什么是
pri
?这只是
priq\u pop
函数中声明的一个指针吗?@haccks它是
priq\u pop
的一个参数,显然用于存储返回的项目的优先级。谢谢,它看起来像是解决我的问题的正确方法:)但是你能给我一个提示吗,如何创建要推送到队列中的字符串副本?如果您的环境具有
strdup
,这是最简单的方法:
strdup(string)
will
malloc
内存并将字符串复制到其中。由您稍后
释放该内存。否则,此链接显示了一种编写自己的
strdup
的方法:因此,如果我的队列中有数百个元素,那么我必须拥有包含这些元素副本的数组,对吗?
strdup
函数将使用
malloc
为每个字符串分配内存。不需要制作单独的阵列来存储这些副本;它们将被分配到堆上。你需要做的唯一一件事就是当你用完它们时,把它们释放出来。(也就是说,调用
free()
,在处理完字符串后向其传递一个指向该字符串副本的指针。)
priq_push(qq, "test2", 2);
priq_push(qq, "test,s", 0);