基本上,這段代碼失敗并出現一個非常奇怪的錯誤:
<source>:75:29: error: cannot convert 'get_view<main()::<unnamed struct>, run_time::data_view>::operator()(const main()::<unnamed struct>&) const::View::code' from type 'int (get_view<main()::<unnamed struct>, run_time::data_view>::operator()(const main()::<unnamed struct>&) const::View::)() const' to type 'int'
75 | return data.code;
https://godbolt.org/z/T3h1a7zne
template <typename SourceT, typename ViewT>
struct get_view;
template <typename SourceT>
struct get_view<SourceT, SourceT>
{
constexpr decltype(auto) operator()(const SourceT &source) const
{
return source;
}
};
// api.h
#include <iostream>
class compile_time
{
public:
template <typename DataT>
void operator()(const DataT &data) const
{
std::cout << "compile-time: " << data.code << std::endl;
}
};
class run_time
{
// How to make data_view private?
// private:
public:
class data_view;
public:
template <typename DataT>
void operator()(const DataT &data) const
{
(*this)(get_view<DataT, data_view>{}(data));
}
private:
void operator()(const data_view &data) const;
};
class run_time::data_view
{
public:
virtual int code() const = 0;
protected:
~data_view() = default; // do not own this
};
template <typename DataT>
struct get_view<DataT, run_time::data_view>
{
// don't want to return std::unique_ptr<data_view>
auto operator()(const DataT &data) const
{
struct View : run_time::data_view {
const DataT& data;
View(const DataT &data)
: data(data)
{}
int code() const override
{
return data.code;
}
};
return View(data);
}
};
// .cpp
void run_time::operator()(const run_time::data_view &dataView) const
{
std::cout << "run-time: " << dataView.code() << std::endl;
}
// main.cpp
int main()
{
struct {
double irrelevant;
int code;
} data{42, 815};
compile_time{}(data);
run_time{}(data); // does not compile!!!
return 0;
}
我找不到它的解釋。為什么說它data.code是函式型別?
有可能完成這項作業嗎?我不想data_view以std::unique_ptr.
我的期望:
get_view部分特化后為run_time::data_viewdata_view完整型別。operator()(const DataT &)在main::<unnamed struct>(即data)被創建之后是特化的,所以它也是一個完整的型別。auto可以推匯出:兩者data_view都是DataT完整的const run_time::data_view &是回傳的本地結構的公共基礎,因此物件的參考是可隱式轉換的
那么任何人都可以解釋它失敗的原因以及如何在不訴諸堆分配的情況下使其作業嗎?(run_time::data_view應該是私有的。我不希望它在類或指定配接器之外的任何地方使用get_view)。
這有效:
template <typename DataT>
void operator()(const DataT &data) const
{
const data_view &view = get_view<DataT, data_view>{}(data);
(*this)(view);
}
我猜它會導致遞回,因為autodeduced fromget_view不是 type const data_view&。所以編譯器operator()(data)對呼叫哪個感到困惑。通過顯式轉換為參考,它變得清晰。
但是,有一個問題是為什么它決定首先使用模板,而不是使用 const 參考的多載。
uj5u.com熱心網友回復:
該問題是由函式決議期間的歧義引起的:
按值get_view回傳一個deduced適合 的型別
template <typename DataT> operator()(const DataT &),從而忽略現有的多載operator()(const data_view &)。
在呼叫運算子之前提供顯式轉換可以解決問題。
template <typename DataT>
void operator()(const DataT &data) const
{
const data_view &view = get_view<DataT, data_view>{}(data);
(*this)(view);
}
轉載請註明出處,本文鏈接:https://www.uj5u.com/ruanti/476409.html
上一篇:不能為從模板化基派生的類的shared_ptr推匯出模板引數
下一篇:處理自定義矢量類
