我將對指標變數的參考傳遞給函式。該函式將執行某些操作并將指標變數指向某個物件。代碼:
int Foo(Obj* &ptr) {
// do something...
ptr = some_address;
return return_value;
}
int main() {
Obj* p = nullptr;
int ret = Foo(p);
// do something with ret
p->DoSomething();
}
但是,如果我想傳遞對 const 指標的參考,事情會變得更加棘手。我希望更改指標變數本身(因此是參考),但我不希望Obj使用此指標更改指向的實體。在我的想象中,它應該是這樣的:
int Foo(const Obj* &ptr) {
// do something...
ptr = some_address;
return return_value;
}
int main() {
const Obj* p = nullptr;
int ret = Foo(p);
// do something with ret
p->DoSomething(); // this should only work when DoSomething() is const method
}
編輯:以下錯誤無法重現,因此被洗掉。這個問題關注的是指標參考的概念,而不是解決一個問題
C 給出了這個編譯錯誤:
main.cpp:22:10: error: cannot bind non-const lvalue reference of type ‘const Obj*&’ to an rvalue of type ‘const Obj*’ 22 | Foo(ptr); | ^~~ main.cpp:14:23: note: initializing argument 1 of ‘void test(const Obj*&)’ 14 | int Foo(const Obj* &ptr) { | ~~~~~~~~~~~~^~~
一些想法:
錯誤無法重現
- 我相信當我嘗試將“未命名變數”傳遞給參考引數時會顯示此錯誤。在這種情況下,我正在傳遞變數
ptr,這應該不是問題。
ptr作為引數傳入,因為該函式有一個有用的回傳值。設定ptr更像是這個功能的副產品,呼叫者可以選擇忽略或使用。我也可以嘗試使用
Obj**作為引數,它是通過指標而不是通過參考傳遞。這在 aconst Obj**作為引數傳遞時有效。我只是想知道如果通過參考傳遞引數會是什么情況。
uj5u.com熱心網友回復:
我不確定您的問題是什么,因為給出的錯誤代碼與您的代碼不匹配。
你的第二個例子int Foo(const Obj* &ptr)完全按照預期作業,如果你 make DoSomethingconst編譯得很好。
評論你的三個想法:
- 如果你正確地構造東西,錯誤就會消失。
- 我真的,真的不喜歡這樣的外引數。回傳一個結構體或一對 int 和指標要干凈得多。這樣呼叫者就可以撰寫
const auto[ret, p] = Foo();而不必顯式宣告您可能不想使用的指標。 - 將指標傳遞給指標是 C 風格的,因為缺少參考,只會使代碼更難閱讀,沒有任何好處。
下面是稍微修改過的代碼,可以很好地編譯,也有更好的 Foo,如我對 2. 的回答中所述:
#include <utility>
struct Obj
{
void DoSomething() const;
};
// This is ugly of course, used just to have a valid ptr to return
Obj global;
int Foo(const Obj* &ptr) {
// do something...
ptr = &global;
return 5;
}
std::pair<int, const Obj*> BetterFoo()
{
// do something...
return {5, &global};
}
int main() {
const Obj* p1 = nullptr;
int ret1 = Foo(p1);
const auto[ret2, p2] = BetterFoo();
p1->DoSomething();
p2->DoSomething();
}
uj5u.com熱心網友回復:
處理這種情況的一種方法是使用typedef或using。例如,using ObjPtr = Obj*;現在函式將是int Foo(const ObjPtr& ptr) { ... }.
轉載請註明出處,本文鏈接:https://www.uj5u.com/shujuku/342869.html
