Commit cbebf885 authored by Dominik Charousset's avatar Dominik Charousset

Allow move-only types in behavior, close #633

parent 08185596
...@@ -54,8 +54,8 @@ public: ...@@ -54,8 +54,8 @@ public:
/// The list of arguments can contain match expressions, message handlers, /// The list of arguments can contain match expressions, message handlers,
/// and up to one timeout (if set, the timeout has to be the last argument). /// and up to one timeout (if set, the timeout has to be the last argument).
template <class T, class... Ts> template <class T, class... Ts>
behavior(const T& x, const Ts&... xs) { behavior(T x, Ts&&... xs) {
assign(x, xs...); assign(std::move(x), std::forward<Ts>(xs)...);
} }
/// Creates a behavior from `tdef` without message handler. /// Creates a behavior from `tdef` without message handler.
...@@ -66,9 +66,9 @@ public: ...@@ -66,9 +66,9 @@ public:
/// Assigns new handlers. /// Assigns new handlers.
template <class... Ts> template <class... Ts>
void assign(const Ts&... xs) { void assign(Ts&&... xs) {
static_assert(sizeof...(Ts) > 0, "assign() called without arguments"); static_assert(sizeof...(Ts) > 0, "assign() called without arguments");
impl_ = detail::make_behavior(xs...); impl_ = detail::make_behavior(std::forward<Ts>(xs)...);
} }
inline void swap(behavior& other) { inline void swap(behavior& other) {
......
...@@ -79,8 +79,6 @@ public: ...@@ -79,8 +79,6 @@ public:
return timeout_; return timeout_;
} }
virtual pointer copy(const generic_timeout_definition& tdef) const = 0;
pointer or_else(const pointer& other); pointer or_else(const pointer& other);
protected: protected:
...@@ -165,9 +163,6 @@ public: ...@@ -165,9 +163,6 @@ public:
call_timeout_handler(cases_, token); call_timeout_handler(cases_, token);
} }
typename behavior_impl::pointer
copy(const generic_timeout_definition& td) const override;
private: private:
void init() { void init() {
std::integral_constant<size_t, 0> first; std::integral_constant<size_t, 0> first;
...@@ -212,24 +207,17 @@ struct behavior_factory { ...@@ -212,24 +207,17 @@ struct behavior_factory {
} }
}; };
template <class... Ts>
typename behavior_impl::pointer
default_behavior_impl<std::tuple<Ts...>>::copy(const generic_timeout_definition& td) const {
using tuple_type = typename with_generic_timeout<has_timeout, std::tuple<Ts...>>::type;
behavior_factory<tuple_type> factory;// = &make_counted<default_behavior_impl<tuple_type>>;
typename il_range<0, num_cases>::type indices;
return apply_args_suffxied(factory, indices, cases_, td);
}
struct make_behavior_t { struct make_behavior_t {
constexpr make_behavior_t() { constexpr make_behavior_t() {
// nop // nop
} }
template <class... Ts> template <class... Ts>
intrusive_ptr<default_behavior_impl<std::tuple<typename lift_behavior<Ts>::type...>>> intrusive_ptr<
default_behavior_impl<std::tuple<typename lift_behavior<Ts>::type...>>>
operator()(Ts... xs) const { operator()(Ts... xs) const {
using type = default_behavior_impl<std::tuple<typename lift_behavior<Ts>::type...>>; using type =
default_behavior_impl<std::tuple<typename lift_behavior<Ts>::type...>>;
return make_counted<type>(std::move(xs)...); return make_counted<type>(std::move(xs)...);
} }
}; };
......
...@@ -43,10 +43,6 @@ public: ...@@ -43,10 +43,6 @@ public:
return second->handle_timeout(); return second->handle_timeout();
} }
pointer copy(const generic_timeout_definition& tdef) const override {
return new combinator(first, second->copy(tdef));
}
combinator(pointer p0, const pointer& p1) combinator(pointer p0, const pointer& p1)
: behavior_impl(p1->timeout()), : behavior_impl(p1->timeout()),
first(std::move(p0)), first(std::move(p0)),
......
/******************************************************************************
* ____ _ _____ *
* / ___| / \ | ___| C++ *
* | | / _ \ | |_ Actor *
* | |___ / ___ \| _| Framework *
* \____/_/ \_|_| *
* *
* Copyright (C) 2011 - 2017 *
* Dominik Charousset <dominik.charousset (at) haw-hamburg.de> *
* *
* Distributed under the terms and conditions of the BSD 3-Clause License or *
* (at your option) under the terms and conditions of the Boost Software *
* License 1.0. See accompanying files LICENSE and LICENSE_ALTERNATIVE. *
* *
* If you did not receive a copy of the license files, see *
* http://opensource.org/licenses/BSD-3-Clause and *
* http://www.boost.org/LICENSE_1_0.txt. *
******************************************************************************/
#define CAF_SUITE behavior
#include "caf/config.hpp"
#include "caf/test/unit_test.hpp"
#include <functional>
#include "caf/behavior.hpp"
#include "caf/message_handler.hpp"
#include "caf/make_type_erased_tuple_view.hpp"
using namespace caf;
using namespace std;
using hi_atom = atom_constant<atom("hi")>;
using ho_atom = atom_constant<atom("ho")>;
namespace {
class nocopy_fun {
public:
nocopy_fun() = default;
nocopy_fun(nocopy_fun&&) = default;
nocopy_fun& operator=(nocopy_fun&&) = default;
nocopy_fun(const nocopy_fun&) = delete;
nocopy_fun& operator=(const nocopy_fun&) = delete;
int operator()(int x, int y) {
return x + y;
}
};
struct fixture {
message m1 = make_message(1);
message m2 = make_message(1, 2);
message m3 = make_message(1, 2, 3);
};
} // namespace <anonymous>
CAF_TEST_FIXTURE_SCOPE(behavior_tests, fixture)
CAF_TEST(default_construct) {
behavior f;
CAF_CHECK_EQUAL(f(m1), none);
CAF_CHECK_EQUAL(f(m2), none);
CAF_CHECK_EQUAL(f(m3), none);
}
CAF_TEST(nocopy_function_object) {
behavior f{nocopy_fun{}};
CAF_CHECK_EQUAL(f(m1), none);
CAF_CHECK_EQUAL(to_string(f(m2)), "*(3)");
CAF_CHECK_EQUAL(f(m3), none);
}
CAF_TEST(single_lambda_construct) {
behavior f{[](int x) { return x + 1; }};
CAF_CHECK_EQUAL(to_string(f(m1)), "*(2)");
CAF_CHECK_EQUAL(f(m2), none);
CAF_CHECK_EQUAL(f(m3), none);
}
CAF_TEST(multiple_lambda_construct) {
behavior f{
[](int x) { return x + 1; },
[](int x, int y) { return x * y; }
};
CAF_CHECK_EQUAL(to_string(f(m1)), "*(2)");
CAF_CHECK_EQUAL(to_string(f(m2)), "*(2)");
CAF_CHECK_EQUAL(f(m3), none);
}
CAF_TEST_FIXTURE_SCOPE_END()
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment