类名 SerialNow = *((类名*)ptr); vs className &SerialNow = *((className*)ptr);
className SerialNow = *((className*)ptr); vs className &SerialNow = *((className*)ptr);
将指针转换为对象时使用或不使用引用有什么区别?
void someClass::method() {
xTaskCreatePinnedToCore(someTaskHandler,"SerialNowTaskTX",XT_STACK_MIN_SIZE*3,this,4,&taskHandleTX,0); // passing 'this' to task handler
}
void someTaskHandler(void *p) {
SerialNow_ SerialNow = *((SerialNow_*)p); // compile but not working properly
SerialNow_ &SerialNow = *((SerialNow_*)p); // compile and working
SerialNow_ *SerialNow = ((SerialNow_*)p); // compile and working but I prefer . over ->
int A = SerialNow.somethingA;
SerialNow.somethingB();
while(1) {
}
vTaskDelete(NULL);
}
案例一
这里我们考虑语句:
SerialNow_ SerialNow = *((SerialNow_*)p);
这里 void*
p
被转换(使用 explicit type conversion)到 SerialNow_*
。接下来,结果 SerialNow_*
被 取消引用 使用 *operator
导致类型为 SerialNow_
的对象。
最后,生成的 SerialNow_
对象用作 初始化器 以初始化左侧名为 SerialNow
的对象。新初始化的对象 SerialNow
是原始对象的副本。这意味着如果您对 SerialNow
进行更改,它不会影响 p
.
指向的原始对象
案例二
这里我们考虑语句:
SerialNow_ &SerialNow = *((SerialNow_*)p);
在这种情况下,除了这次 SerialNow
是结果对象的 别名 之外,大部分过程与情况 1 相同。这与情况 1 的不同之处仅在于,在情况 1 中,左侧的对象 SerialNow
是原始对象的副本,而此处左侧的 SerialNow
是对对象的左值引用原始对象。这意味着如果您对 SerialNow
进行更改,它将影响 p
.
指向的原始对象
案例三
这里我们考虑语句:
SerialNow_ *SerialNow = ((SerialNow_*)p);
此处 void*
p
被转换为 SerialNow_*
。但是与情况 1 和情况 2 不同,结果指针 未取消引用 。因此,此处左侧名为 SerialNow
的对象是根据显式类型产生的指针初始化的转换。
此外,SerialNow
是显式类型转换产生的指针副本..
初步评论
首先,请记住,转换 void*
指针在 C++ 中是一件相当危险的事情,如果指向的对象与您要转换为的类型不兼容,则可能是 UB。
而不是括号之间的 C-like 强制转换,更喜欢 C++ 更明确的强制转换,这样可以更好地显示危险级别。如果 p 是多态基类型,最好使用更安全的 dynamic_cast
. Otherwise use a static_cast
to avoid some common mistakes. Only in last resort use reinterpret_cast
,但您必须真正确定自己在做什么。
你们的说法有什么不同?
如果我们假设 p 是指向与 SerialNow_
兼容的类型的有效指针,这就是您不同语句的含义:
SerialNow_ SerialNow = *((SerialNow_*)p);
第一个复制p指向的对象。如果以后更改b指向的对象的内容,对对象SerialNow
没有影响。请记住,如果 p 指向的对象不是 SerialNow_
而是子类,则可能会出现 slicing。
SerialNow_ &SerialNow = *((SerialNow_*)p);
第二个创建引用 p 指向的对象。您可以将 SerialNow
当作一个对象来使用,但实际上它指的是与 p:
指向的对象相同的对象
SerialNow_ *SerialNow = ((SerialNow_*)p);
第三个创建一个指向p指向的对象的指针:
第二个和第三个尊重多态性。如果 p 指向的对象不是 SerialNow_
而是子类型,多态性将起作用,即如果调用虚函数,将调用与对象的真实 run-time 类型对应的函数。
将指针转换为对象时使用或不使用引用有什么区别?
void someClass::method() {
xTaskCreatePinnedToCore(someTaskHandler,"SerialNowTaskTX",XT_STACK_MIN_SIZE*3,this,4,&taskHandleTX,0); // passing 'this' to task handler
}
void someTaskHandler(void *p) {
SerialNow_ SerialNow = *((SerialNow_*)p); // compile but not working properly
SerialNow_ &SerialNow = *((SerialNow_*)p); // compile and working
SerialNow_ *SerialNow = ((SerialNow_*)p); // compile and working but I prefer . over ->
int A = SerialNow.somethingA;
SerialNow.somethingB();
while(1) {
}
vTaskDelete(NULL);
}
案例一
这里我们考虑语句:
SerialNow_ SerialNow = *((SerialNow_*)p);
这里 void*
p
被转换(使用 explicit type conversion)到 SerialNow_*
。接下来,结果 SerialNow_*
被 取消引用 使用 *operator
导致类型为 SerialNow_
的对象。
最后,生成的 SerialNow_
对象用作 初始化器 以初始化左侧名为 SerialNow
的对象。新初始化的对象 SerialNow
是原始对象的副本。这意味着如果您对 SerialNow
进行更改,它不会影响 p
.
案例二
这里我们考虑语句:
SerialNow_ &SerialNow = *((SerialNow_*)p);
在这种情况下,除了这次 SerialNow
是结果对象的 别名 之外,大部分过程与情况 1 相同。这与情况 1 的不同之处仅在于,在情况 1 中,左侧的对象 SerialNow
是原始对象的副本,而此处左侧的 SerialNow
是对对象的左值引用原始对象。这意味着如果您对 SerialNow
进行更改,它将影响 p
.
案例三
这里我们考虑语句:
SerialNow_ *SerialNow = ((SerialNow_*)p);
此处 void*
p
被转换为 SerialNow_*
。但是与情况 1 和情况 2 不同,结果指针 未取消引用 。因此,此处左侧名为 SerialNow
的对象是根据显式类型产生的指针初始化的转换。
此外,SerialNow
是显式类型转换产生的指针副本..
初步评论
首先,请记住,转换 void*
指针在 C++ 中是一件相当危险的事情,如果指向的对象与您要转换为的类型不兼容,则可能是 UB。
而不是括号之间的 C-like 强制转换,更喜欢 C++ 更明确的强制转换,这样可以更好地显示危险级别。如果 p 是多态基类型,最好使用更安全的 dynamic_cast
. Otherwise use a static_cast
to avoid some common mistakes. Only in last resort use reinterpret_cast
,但您必须真正确定自己在做什么。
你们的说法有什么不同?
如果我们假设 p 是指向与 SerialNow_
兼容的类型的有效指针,这就是您不同语句的含义:
SerialNow_ SerialNow = *((SerialNow_*)p);
第一个复制p指向的对象。如果以后更改b指向的对象的内容,对对象SerialNow
没有影响。请记住,如果 p 指向的对象不是 SerialNow_
而是子类,则可能会出现 slicing。
SerialNow_ &SerialNow = *((SerialNow_*)p);
第二个创建引用 p 指向的对象。您可以将 SerialNow
当作一个对象来使用,但实际上它指的是与 p:
SerialNow_ *SerialNow = ((SerialNow_*)p);
第三个创建一个指向p指向的对象的指针:
第二个和第三个尊重多态性。如果 p 指向的对象不是 SerialNow_
而是子类型,多态性将起作用,即如果调用虚函数,将调用与对象的真实 run-time 类型对应的函数。