簡體   English   中英

獲取成員函數的decltype?

[英]Getting the decltype of a member function?

所以下面的代碼效果很好:

void function() { }
std::cout << typeid(decltype(function)).name() << '\n';

但以下代碼無法編譯:

struct object {
    void function() { }
}
std::cout << typeid(decltype(object::function)).name() << '\n';

為什么?

成員函數有一個類型,就像普通函數有一個類型一樣,對吧? 我假設它看起來像這樣:

void func(object*, void)

奇怪的是,我可以通過以下方式獲得指針:

decltype(&object::function)

最終是這樣的:

void (__thiscall object::*)(void)

如果我能得到指向它的指針,為什么我不能得到它的類型? 就像我可以使用正常功能一樣。 在獲得指向成員函數類型的指針后,我嘗試刪除指針:

template <typename T>
struct remove_pointer { using type = T; }

template <typename T>
struct remove_pointer<T*> { using type = T; }

std::cout << typeid(remove_pointer<decltype(&object::function)>::type).name() << '\n';

它不會刪除指針,但不會導致編譯失敗,它只是打印出與我不嘗試刪除指針時相同的內容。

這一切都非常令人困惑,有人可以幫我理解為什么我無法訪問成員函數的實際類型嗎?

成員指針不是指針。 要從類型中刪除一個,您需要這樣的東西:

template <typename> struct RemoveMemPtr {};
template <typename X, typename Y> struct RemoveMemPtr<X Y::*> {using type = X;};

但是,這不會為您提供任何新信息。 給定ReturnType (Class::*)(Params...) ,它將只返回ReturnType(Params...) ,類似於如何將常規函數指針類型轉換為函數。


decltype(object::function)不能僅僅因為標准這樣說而起作用。 當你命名一個成員函數時,你必須要么立即調用它,要么形成一個指向它的指針。


成員函數在形式上確實有一個 type ,但是除了形成一個成員指針並從中剝離指針部分之外,沒有辦法確定這種類型。 它與具有相同簽名的自由函數的類型相同(不包括隱式this參數)。 除了成員函數可以有const / volatile / & / &&限定符,而自由函數不能。

作為一件瑣事,您可以使用這些類型來聲明成員函數:

using F = void(int) const;

struct A
{
    F func; // void func(int) const;
};

您的remove_pointer名稱錯誤。 它將類型“指向類object類型T的成員的指針”轉換為T ,它與原始類型沒有直接關系,並且與該類型的實體不兼容。 關於原始object是對象成員的關鍵信息丟失了。 模板最好命名為remove_membership類的名稱。

例如,它將&object::function的類型void (object::*)()轉換為void() 目前尚不清楚為什么在使用object::function時需要void() ,因為它與void()無論如何都不兼容。

刪除成員資格是一個重要的、通常不是有用的轉換,因此沒有內置的語法來實現它。 如果您需要它,您只需編寫一個模板即可。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM