解除引用的指针构造的地址

时间:2016-08-12 09:57:26

标签: c pointers syntax dereference addressof

unqlite c库中,我找到了以下代码:

 pObj = jx9VmReserveMemObj(&(*pVm),&nIdx);

其中pVm是:

typedef struct jx9_vm jx9_vm;
jx9_vm *pVm

和被调用的函数声明为:

jx9_value * jx9VmReserveMemObj(jx9_vm *, sxu32 *);

构建&(*pVm)的内容在调用中使用而不仅仅是pVm&(*pVm)是否等同于pVm

3 个答案:

答案 0 :(得分:8)

引用C11,章节§6.5.3.2,地址和间接操作符

  

[...]如果操作数是一元*运算符的结果,   既不评估该运算符也不评估&运算符,结果就像两者都一样   省略,但运算符上的约束仍然适用且结果不是左值。 [...]

所以,,它们等效

但是,可以使用此构造来检查针对指针类型的参数类型。从一元*运算符的属性

  

一元*运算符的操作数应具有指针类型。

所以,构造&(*pVm)

    如果pvm是指针或数组名称,
  • 就可以了。
  • 如果pvm是非指针类型变量,
  • 将生成编译器错误。

有关代码示例,请参阅the other answer by Alter Mann

另一个区别(一般)是,pVm可以分配(可以用作赋值运算符的LHS),但是{{1不能。

答案 1 :(得分:4)

  

&(*pVm)是否等同于pVm

是。 * 1

*(&pVm)相同。

(* 1) 由于* - 运算符( de-referencing )仅适用于指针,因此前一个构造仅适用于指针(或数组,它会衰减到指向其第一个元素的指针) )。后者可以应用于任何类型的变量。

答案 2 :(得分:2)

是的,它们是相同的,但请注意,当对象不是数组或指针时它会失败:

#include <stdio.h>

struct t {
    int value;
};

typedef struct t t;

int func(t *ptr)
{
    return ptr->value;
}

int main(void)
{
    t o = {.value = 0};
    t v[2] = {{.value = 1}, {.value = 2}};

    printf("%d\n", func(&(*o))); /* error: invalid type argument of unary ‘*’ */
    printf("%d\n", func(&(*v))); /* WORKS */
    return 0;
}