1 | /////////////////////////////////////////////////////////////////////////////// |
2 | // constrained_ops.cpp |
3 | // |
4 | // Copyright 2010 Thomas Heller |
5 | // Copyright 2011 Eric Niebler |
6 | // |
7 | // Distributed under the Boost Software License, Version 1.0. (See accompanying |
8 | // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) |
9 | |
10 | #include <boost/proto/proto.hpp> |
11 | #include <boost/test/unit_test.hpp> |
12 | |
13 | using namespace boost; |
14 | |
15 | typedef proto::terminal<int>::type term; |
16 | |
17 | struct equation; |
18 | |
19 | struct addition: |
20 | proto::or_ |
21 | < |
22 | proto::terminal<proto::_>, |
23 | proto::plus<addition, addition> |
24 | > |
25 | {}; |
26 | |
27 | struct equation: |
28 | proto::or_ |
29 | < |
30 | proto::equal_to<addition, addition> |
31 | > |
32 | {}; |
33 | |
34 | template<class Expr> |
35 | struct extension; |
36 | |
37 | struct my_domain: |
38 | proto::domain |
39 | < |
40 | proto::pod_generator<extension>, |
41 | equation, |
42 | proto::default_domain |
43 | > |
44 | {}; |
45 | |
46 | template<class Expr> |
47 | struct lhs_extension; |
48 | |
49 | struct my_lhs_domain: |
50 | proto::domain |
51 | < |
52 | proto::pod_generator<lhs_extension>, |
53 | addition, |
54 | my_domain |
55 | > |
56 | {}; |
57 | |
58 | template<class Expr> |
59 | struct rhs_extension; |
60 | |
61 | struct my_rhs_domain: |
62 | proto::domain |
63 | < |
64 | proto::pod_generator<rhs_extension>, |
65 | addition, |
66 | my_domain |
67 | > |
68 | {}; |
69 | |
70 | template<class Expr> |
71 | struct extension |
72 | { |
73 | BOOST_PROTO_BASIC_EXTENDS( |
74 | Expr |
75 | , extension<Expr> |
76 | , my_domain |
77 | ) |
78 | |
79 | void test() const |
80 | {} |
81 | }; |
82 | |
83 | template<class Expr> |
84 | struct lhs_extension |
85 | { |
86 | BOOST_PROTO_BASIC_EXTENDS( |
87 | Expr |
88 | , lhs_extension<Expr> |
89 | , my_lhs_domain |
90 | ) |
91 | }; |
92 | |
93 | template<class Expr> |
94 | struct rhs_extension |
95 | { |
96 | BOOST_PROTO_BASIC_EXTENDS( |
97 | Expr |
98 | , rhs_extension<Expr> |
99 | , my_rhs_domain |
100 | ) |
101 | }; |
102 | |
103 | void test_constrained_ops() |
104 | { |
105 | lhs_extension<term> const i = {}; |
106 | rhs_extension<term> const j = {}; |
107 | |
108 | proto::assert_matches_not<equation>(i); // false |
109 | proto::assert_matches_not<equation>(j); // false |
110 | proto::assert_matches_not<equation>(i + i); // false |
111 | proto::assert_matches_not<equation>(j + j); // false |
112 | #if 0 |
113 | proto::assert_matches_not<equation>(i + j); // compile error (by design) |
114 | proto::assert_matches_not<equation>(j + i); // compile error (by design) |
115 | #endif |
116 | proto::assert_matches<equation>(i == j); // true |
117 | proto::assert_matches<equation>(i == j + j); // true |
118 | proto::assert_matches<equation>(i + i == j); // true |
119 | proto::assert_matches<equation>(i + i == j + j); // true |
120 | } |
121 | |
122 | using namespace boost::unit_test; |
123 | /////////////////////////////////////////////////////////////////////////////// |
124 | // init_unit_test_suite |
125 | // |
126 | test_suite* init_unit_test_suite( int argc, char* argv[] ) |
127 | { |
128 | test_suite *test = BOOST_TEST_SUITE("test constrained EDSLs" ); |
129 | test->add(BOOST_TEST_CASE(&test_constrained_ops)); |
130 | return test; |
131 | } |
132 | |