簡體   English   中英

如何使編譯器選擇非成員 function 重載

[英]How to make compiler choose a non-member function overload

我正在編寫一個庫,它對內置類型(int、float、double 等)和用戶提供的類型執行一些操作。 其中一個由模板 function 執行:

namespace lib
{
template<typename T>
inline auto from_string(std::string const & s, T & t) -> bool
{
    std::istringstream iss(s);
    iss >> t;
    return !iss.fail();
}
}

這是一個自定義點——用戶可以為他們的類型重載這個函數:

namespace foo
{
class UserType
{
    // (...)
};
}

namespace lib
{
inline auto from_string(std::string const & s, foo::UserType & ut) -> bool
{
    // some implementation
}
}

或將from_string function 放在同一個命名空間中並通過 ADL 訪問:

namespace foo
{
inline auto from_string(std:string const & s, UserType & ut) -> bool
{
    // some implementation
}
}
}

現在,除了字符串到類型的轉換之外,該庫還執行類型到字符串、比較和更多操作。 我想通過一系列將值保存為std::any實例的類來完成它:

namespace lib
{
class TypeHandler
{
    public:
        virtual TypeHandler() = default;
        virtual auto from_string(std::string const & string, std::any & value) const -> bool = 0;
        // more functions
};

template<typename T>
class TypeHandlerT : public TypeHandler
{
    public:
        auto from_string(std::string const & string, std::any & value) const -> bool override
        {
            T val;
            if (from_string(string, val))  // an attempt to call the free function
            {
                value = val;
                return true;
            }
            return false;
        }
}
}

為了方便起見,我想使用TypeHandlerT類。

但是,使用這樣的代碼,當我嘗試使用TypeHandlerT<int>時會出現以下編譯器錯誤:

error C2664: 'bool lib::TypeHandlerT<T>::from_string(const std::string &,std::any &) const':
cannot convert argument 2 from 'T' to 'std::any &' with [ T=int ]

似乎from_string的成員版本隱藏了免費的 function 版本。

有沒有辦法優雅地解決這個問題? 例如,將免費的 function 帶入 scope (但如何在不排除 ADL 的情況下做到這一點?)?

我知道一個簡單的解決方法是重命名成員或免費 function,但我想避免這種情況。

Scope 從TestHandlerT<T>::from_string的主體開始的查找在成員 function 命中lib::from_string之前命中。 因此,只需usinglib::from_string重新引入主體的 scope 即可。 這也會重新啟用 ADL,因為當基於 scope 的查找命中 class 成員時,ADL 會被抑制。

template<typename T>
struct TypeHandlerT : TypeHandler {
    bool from_string(std::string const &string, std::any &value) const -> override {
        using lib::from_string;
        T val;
        if (from_string(string, val)) {
            value = val;
            return true;
        }
        return false;
    }
};

暫無
暫無

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

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