在C语言中将double转换为void*

7
我正在编写一个解释器,希望能够将函数返回的任何值存储到void指针中。我没有问题将int和各种指针存储为void指针,但是当尝试将double转换为void指针时会出现错误。我知道double在位级别上与整数和指针存储方式不同,但是我不明白为什么我不能将任何想要的位放入指针中(假设已分配足够的内存),然后稍后将它们取出,并将它们作为double进行转换。
是否有可能使用我不知道的语法将double强制转换为void指针,或者我对void指针的工作原理存在误解?

4
你考虑过使用“联合体(union)”吗? - Andre Holzner
5
听起来你正在做一些极其错误的事情。请查看David的回答。 - pmr
请检查我在另一个问题中的答案:http://stackoverflow.com/questions/6539023/storing-values-in-union-in-c/6539185#6539185 - Vinicius Kamakura
4个回答

16

在许多系统上,一个double是8个字节长,而指针则是4个字节长。因此,前者不能适应后者。

你似乎滥用了void*。你的解决方案将涉及分配存储空间,至少要和你需要存储在某个类似于变体结构中的最大类型一样大,例如一个union


2
我简直不敢相信我以前从未听说过联合体。这正是我一直在寻找的。 - Jack

3

当然可以进行类型转换。在C语言中,无类型指针是实现多态的关键。但是需要提前知道传递给函数的内容。

void *p_v ;
double *p_d ;
p_d = malloc( sizeof( double ) ) ;
p_v = ( void * ) p_d ;

2
你的示例似乎可以工作,因为p_d是一个指针。但是提问者询问的是非指针到void*的转换。 - user2074102

-1

继续与Fabio合作,并确保您正在x64上运行

int main()
{
    double d = 1.00e+00; // 0x3ff0000000000000
    double* pd = &d;
    void** p = (void**)pd;
    void* dp = *p;
    printf("%f %p %p %p \n", d, pd, p, dp);

    printf("%d %f\n", dp, *(double*)p);

    printf("%f\n", *(double*)(void **)&d);
}

输出

1.000000 0000000353F1FA30 0000000353F1FA30 3FF0000000000000
0 1.000000
1.000000

-3

这是它

int main ( ) {
    double d = 1.00e+00 ; // 0x3ff0000000000000
    double * pd = & d ;
    void * * p = ( void * * ) pd ;
    void * dp = * p ;
    printf ( "%f %p %p %p \n" , d , pd , p , dp ) ;
    return 0 ;
} ;

输出

1.000000 0x7fff89a7de80 0x7fff89a7de80 0x3ff0000000000000

第二个和第三个地址可能不同。一个快捷方式

void * dp = * ( void * * ) & d ;

干杯


这是未定义行为(严格别名违规)。 - M.M
@M.M 不是这样的。我在进行指针转换,我知道自己在做什么,这不是C++,它可以编译并给出正确的输出。我不建议在长代码中使用这种技术,但我是正确的。 - Fabio
表达式 *p 具有类型 void *,但正在访问实际类型为 double * 的内存。它们甚至可能具有不同的大小。 - M.M
你是对的,我假设所有东西都是64位对齐的...否则你需要使用给定长度的pchar进行迭代读取。 - Fabio
1
*(void **)&d是未定义行为,并且违反了严格别名规则。 - S.S. Anne

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接