namespace bcc0 {
class task {
// Need implementation here
public:
task() = default;
task(const task&) = delete;
task(task&&) noexcept = default;
task& operator=(const task&) = delete;
task& operator=(task&&) noexcept = default;
template <class F> // F model void()
task(F f); // Need to implement
void operator()(); // Need to implement
};
} // namespace bcc0
namespace bcc {
class task {
struct concept;
template <class F>
struct model;
std::unique_ptr<concept> _self;
public:
task() = default;
//...
template <class F> // F model void()
task(F f); // Need to implement
void operator()(); // Need to implement
};
} // namespace bcc
struct task::concept {
virtual ~concept() {}
virtual void invoke() = 0;
};
template <class F>
struct task::model final : concept {
F _f;
model(F f) : _f(move(f)) {}
void invoke() override { _f(); }
};
template <class F>
task::task(F f) : _self(make_unique<model<F>>(move(f))) { }
namespace bcc {
void task::operator()() { _self->invoke(); }
} // namespace bcc
class sequential_process {
// using task = function<void()>;
{
sequential_process process;
auto future = async_packaged(process, []{ return "Hello World!"s; });
cout << future.get() << endl;
}
get()
on a future once{
sequential_process process;
auto future = async_packaged(process, []{ return "Hello World!"s; });
cout << future.get() << endl;
cout << future.get() << endl; // Will throw!
}
std::shared_future<>
std::optional<>
(C++17)namespace v0 {
class interned_string {
struct shared_pool {
mutex _mutex;
unordered_set<string> _pool;
const string* insert(const string& a) {
lock_guard<mutex> lock(_mutex);
return &*_pool.insert(a).first;
}
};
static auto pool() -> shared_pool& {
static shared_pool result;
return result;
}
const std::string* _string;
public:
interned_string(const string& a) : _string(pool().insert(a)) {}
const string& str() const { return *_string; }
};
} // namespace v0
struct shared_pool {
unordered_set<string> _pool;
sequential_process _process;
auto insert(string a) -> future<const string*> {
return async_packaged(_process, [this, _a = move(a)]() mutable {
return &*_pool.insert(move(_a)).first;
});
}
};
namespace v1 {
class interned_string {
// struct shared_pool
static auto pool() -> shared_pool& {
static shared_pool result;
return result;
}
shared_future<const std::string*> _string;
public:
interned_string(string a) : _string(pool().insert(move(a))) {}
const string& str() const { return *_string.get(); }
};
} // namespace v1
std::future<>
in C++11-17 is very limited
interned_string::str()
to return a futureget()
meansshared_future
imposes additional costsPros: