[英]operator-> for an iterator that returns a temporary
我有一個數據結構,它本質上是一個 hash 表。 出於緩存原因,鍵和值分開存儲。 我有一個遍歷容器並在取消引用時返回鍵和值對的迭代器。
但是,我在讓迭代器表現得像其他迭代器時遇到了一些麻煩。 特別是operator->
。 這是我到目前為止所擁有的:
struct KeyValuePair
{
KeyValuePair(const int& key, int& value) : key(key), value(value) {}
const int& key;
int& value;
};
struct Iterator
{
KeyValuePair operator*() { return KeyValuePair(*keys, *values); }
// TODO: Implement this
//KeyValuePair* operator->() { return ... }
int* keys = nullptr;
int* values = nullptr;
};
這適用於 range-for 和顯式取消引用迭代器
auto it = container.begin();
KeyValuePair pair = *it;
但它不適用於“通過”迭代器,因為我沒有operator->
auto it = container.begin();
int& value = it->value;
而且我不知道如何為這個迭代器實現operator->
。 我的第一個想法是在迭代器中插入一個KeyValuePair
並返回一個指向它的指針,但是如果沒有惡作劇就無法重新設置引用。
比我聰明的人有什么提示嗎?
如果您無法從operator->
返回指針,請按值返回一個幫助程序 class。 使 class 存儲一個KeyValuePair
並重載其operator->
以返回指向該對的指針。
我的回答使用了與 RedFog 相同的想法,但我試圖讓代碼不那么復雜。
struct Iterator
{
KeyValuePair operator*() const
{
return KeyValuePair(*keys, *values);
}
class ArrowHelper
{
KeyValuePair value
public:
ArrowHelper(KeyValuePair value) : value(value) {}
KeyValuePair *operator->() const
{
return &value;
}
};
ArrowHelper operator->() const
{
return **this;
}
int* keys = nullptr;
int* values = nullptr;
};
迭代器有時會返回一個臨時的 object 作為“引用”,但是operator->
通常需要一個左值來獲取它的指針。 在這種情況下,為了讓operator->
工作,我們應該提供指針的包裝器: (C++11 版本)
struct KeyValuePair
{
KeyValuePair(const int& key, int& value) : key(key), value(value) {}
const int& key;
int& value;
private:
template<typename T>
struct Helper{
T ref;
T* operator->(){ return std::addressof(ref); }
};
Helper<KeyValuePair> get(){ return Helper<KeyValuePair>{*this}; }
friend struct Iterator;
};
struct Iterator
{
KeyValuePair operator*() { return KeyValuePair(*keys, *values); }
auto operator->()->decltype((*(*this)).get()){
return (*(*this)).get();
}
int* keys = nullptr;
int* values = nullptr;
};
如果“參考” object ( KeyValuePair
) 是可復制構造的,它就可以工作。 Helper
的構造函數中的副本是必需的,因為臨時KeyValuePair
將在返回包裝器后被破壞。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.