在 C 中将 const void * 转换为 const char *
Casting a const void * to a const char * in C
所以我有一个这样的 C 函数:
int cmp (const void *a, const void* b)
return rot13cmp( (const char*)a, (const char*)b );
}
而rot13cmp是另一个接受两个const char *类型参数的函数。
我将此函数传递给 C qsort 函数的比较参数,但它似乎不起作用。
但是,如果我改为通过执行
来转换 const void * 变量
return rot13cmp ( *(const char **)a, *(const char **)b );
然后该功能开始工作。我在 SO 上查看了这个,但每个消息来源都说第一种铸造方法应该有效,所以我想知道为什么只有第二种方法对我有用?
编辑:这是我的相关代码,
int cmp (const void *a, const void *b) {
return rot13cmp( (const char *)a, (const char *)b );
}
int rot13cmp (const char *a, const char *b) {
while (*a == *b && *a != '\n') {
a++;
b++;
}
if (*a == *b) { return 0; }
else if (*a == '\n') { return 1; }
else if (*b == '\n') { return 1; }
else { return rot13(*a) - rot13(*b);
}
and rot13 returns 一个字母的 ASCII 码的 int,它在字母表中旋转了 13 个字母。
我通过
调用了qsort
qsort(words, word_count, sizeof(char*), cmp);
其中 words 是一个 char 数组**,word_count 是一个 int。 cmp 也只是
qsort()
使用指向应比较的数组元素的指针调用比较函数。
如果您的数组包含 const char*
,这意味着使用指向这些指针的指针调用比较函数,您必须相应地进行强制转换和取消引用。
对于 (const char*)a
,您将参数解释为指向 const char
的指针。但事实并非如此。实际上它是指向输入数组中 const char*
的指针。
这就是为什么 (const char**)a
是正确的转换,它将参数解释为指向 const char*
的指针。要进行字符串比较,您需要指向 const char*
,您可以通过使用 *
.
取消引用强制转换值来访问它
您可以将其视为首先更正类型(通过强制转换),然后访问指向的值(通过取消引用)。
这两种尝试的区别在于第二种情况进行了额外的取消引用。这很重要,因为 qsort()
不直接传递 const char*
,而是传递指向它的指针。所以我们必须查看指向的值才能找到我们要找的东西。通过直接转换为 const char*
我们只是声称该变量将包含这样一个指针,这不会很好地结束,因为事实并非如此。
所以我有一个这样的 C 函数:
int cmp (const void *a, const void* b)
return rot13cmp( (const char*)a, (const char*)b );
}
而rot13cmp是另一个接受两个const char *类型参数的函数。
我将此函数传递给 C qsort 函数的比较参数,但它似乎不起作用。
但是,如果我改为通过执行
来转换 const void * 变量return rot13cmp ( *(const char **)a, *(const char **)b );
然后该功能开始工作。我在 SO 上查看了这个,但每个消息来源都说第一种铸造方法应该有效,所以我想知道为什么只有第二种方法对我有用?
编辑:这是我的相关代码,
int cmp (const void *a, const void *b) {
return rot13cmp( (const char *)a, (const char *)b );
}
int rot13cmp (const char *a, const char *b) {
while (*a == *b && *a != '\n') {
a++;
b++;
}
if (*a == *b) { return 0; }
else if (*a == '\n') { return 1; }
else if (*b == '\n') { return 1; }
else { return rot13(*a) - rot13(*b);
}
and rot13 returns 一个字母的 ASCII 码的 int,它在字母表中旋转了 13 个字母。
我通过
调用了qsortqsort(words, word_count, sizeof(char*), cmp);
其中 words 是一个 char 数组**,word_count 是一个 int。 cmp 也只是
qsort()
使用指向应比较的数组元素的指针调用比较函数。
如果您的数组包含 const char*
,这意味着使用指向这些指针的指针调用比较函数,您必须相应地进行强制转换和取消引用。
对于 (const char*)a
,您将参数解释为指向 const char
的指针。但事实并非如此。实际上它是指向输入数组中 const char*
的指针。
这就是为什么 (const char**)a
是正确的转换,它将参数解释为指向 const char*
的指针。要进行字符串比较,您需要指向 const char*
,您可以通过使用 *
.
您可以将其视为首先更正类型(通过强制转换),然后访问指向的值(通过取消引用)。
这两种尝试的区别在于第二种情况进行了额外的取消引用。这很重要,因为 qsort()
不直接传递 const char*
,而是传递指向它的指针。所以我们必须查看指向的值才能找到我们要找的东西。通过直接转换为 const char*
我们只是声称该变量将包含这样一个指针,这不会很好地结束,因为事实并非如此。