使用最新的 msvc(截至 25DEC17)。
template< typename T>
auto out_ (const T & val_)
{
// do something with val_
// error: can not deduce auto from out_
return out_;
}
问题是如何编写代码,然后对上面这个小“东西”写几个重载?
对,必须是msvc和C++17。没有 GCC 7.0.2 也不编译它。 clang 还没试过。
也许仿函数模式可能有所帮助?
请指教...
最佳答案
我很惊讶您的 lambda 解决方案可以与 g++ 一起使用。 clang++ 投诉
error: variable 'out_' declared with deduced type 'auto' cannot appear in its own initializer
return out_ ;
^
我怀疑 clang++ 拒绝你的代码是正确的(g++ 接受它是错误的)但我不确定。
无论如何,我发现 lambda 返回自身的想法很有趣。
我提出了一个基于带有模板的结构的非 lambda(但我希望标准兼容和可移植)解决方案 operator()
返回对象的引用。
我是说
struct outS
{
template <typename T>
outS const & operator() (T const & t) const
{
std::cout << t;
return *this;
}
};
所以你可以写,例如,
outS{}("Hello ")("from ")("GCC ")(__VERSION__)(" !");
std::endl
的问题是不同的。
问题是 std::endl
被定义(见 CPP Reference )为
template< class CharT, class Traits >
std::basic_ostream<CharT, Traits>& endl( std::basic_ostream<CharT, Traits>& os );
即std::endl
是一个模板函数。
你可以写
std::cout << std::endl;
或
std::wcout << std::endl;
因为运算符 <<
选择具体版本std::endl
;但你不能将它传递给 outS
如下
outS{}(std::endl);
因为outS
无法选择 std::endl
的特定版本.
所以你必须明确它;匹配std::endl
与 std::cout
, std::endl
的模板参数是char
和 std::char_traits<char>
.
所以你可以写(丑陋的,我知道)
outS{}(std::endl<char, std::char_traits<char>>);
但是如果你实现一个 struct
基于解决方案 ( outS
),您可以添加 endl()
方法
outS const & endl () const
{
std::cout << std::endl;
return *this;
}
这样你就可以写
outS{}.endl();
下面是一个完整的工作示例
#include <iostream>
struct outS
{
template <typename T>
outS const & operator() (T const & t) const
{
std::cout << t;
return *this;
}
outS const & endl () const
{
std::cout << std::endl;
return *this;
}
};
int main()
{
outS{}("Hello ")("from ")("GCC ")(__VERSION__)(" !").endl();
}
关于c++ - 如何编码和重载返回自身的函数? C++17,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47966347/