]>
git.proxmox.com Git - ceph.git/blob - ceph/src/boost/libs/contract/example/cline90/vstack.cpp
2 // Copyright (C) 2008-2018 Lorenzo Caminiti
3 // Distributed under the Boost Software License, Version 1.0 (see accompanying
4 // file LICENSE_1_0.txt or a copy at http://www.boost.org/LICENSE_1_0.txt).
5 // See: http://www.boost.org/doc/libs/release/libs/contract/doc/html/index.html
9 #include <boost/contract.hpp>
10 #include <boost/optional.hpp>
13 // NOTE: Incomplete contract assertions, addressing only `empty` and `full`.
15 class abstract_stack
{
18 boost::contract::check c
= boost::contract::constructor(this)
20 // AXIOM as empty() cannot actually be checked here to avoid
21 // calling pure virtual function length() during construction).
22 BOOST_CONTRACT_ASSERT_AXIOM(empty());
27 virtual ~abstract_stack() {
28 boost::contract::check c
= boost::contract::destructor(this);
33 boost::contract::check c
= boost::contract::public_function(this)
35 BOOST_CONTRACT_ASSERT(result
== (length() == capacity()));
39 return result
= (length() == capacity());
44 boost::contract::check c
= boost::contract::public_function(this)
46 BOOST_CONTRACT_ASSERT(result
= (length() == 0));
50 return result
= (length() == 0);
53 virtual int length(boost::contract::virtual_
* v
= 0) const = 0;
54 virtual int capacity(boost::contract::virtual_
* v
= 0) const = 0;
56 virtual T
const& item(boost::contract::virtual_
* v
= 0) const = 0;
58 virtual void push(T
const& value
, boost::contract::virtual_
* v
= 0) = 0;
59 virtual T
const& pop(boost::contract::virtual_
* v
= 0) = 0;
61 virtual void clear(boost::contract::virtual_
* v
= 0) = 0;
65 int abstract_stack
<T
>::length(boost::contract::virtual_
* v
) const {
67 boost::contract::check c
= boost::contract::public_function(v
, result
, this)
68 .postcondition([&] (int const& result
) {
69 BOOST_CONTRACT_ASSERT(result
>= 0);
77 int abstract_stack
<T
>::capacity(boost::contract::virtual_
* v
) const {
79 boost::contract::check c
= boost::contract::public_function(v
, result
, this)
80 .postcondition([&] (int const& result
) {
81 BOOST_CONTRACT_ASSERT(result
>= 0);
89 T
const& abstract_stack
<T
>::item(boost::contract::virtual_
* v
) const {
90 boost::optional
<T
const&> result
;
91 boost::contract::check c
= boost::contract::public_function(v
, result
, this)
93 BOOST_CONTRACT_ASSERT(!empty());
101 void abstract_stack
<T
>::push(T
const& value
, boost::contract::virtual_
* v
) {
102 boost::contract::check c
= boost::contract::public_function(v
, this)
104 BOOST_CONTRACT_ASSERT(!full());
107 BOOST_CONTRACT_ASSERT(!empty());
114 T
const& abstract_stack
<T
>::pop(boost::contract::virtual_
* v
) {
115 boost::optional
<T
const&> result
;
116 boost::contract::old_ptr
<T
> old_item
= BOOST_CONTRACT_OLDOF(v
, item());
117 boost::contract::check c
= boost::contract::public_function(v
, result
, this)
119 BOOST_CONTRACT_ASSERT(!empty());
121 .postcondition([&] (boost::optional
<T
const&> const& result
) {
122 BOOST_CONTRACT_ASSERT(!full());
123 BOOST_CONTRACT_ASSERT(*result
== *old_item
);
131 void abstract_stack
<T
>::clear(boost::contract::virtual_
* v
) {
132 boost::contract::check c
= boost::contract::public_function(v
, this)
134 BOOST_CONTRACT_ASSERT(empty());
142 #define BASES private boost::contract::constructor_precondition< \
143 vstack<T> >, public abstract_stack<T>
146 friend class boost::contract::access
;
148 typedef BOOST_CONTRACT_BASE_TYPES(BASES
) base_types
;
151 void invariant() const {
152 BOOST_CONTRACT_ASSERT(length() >= 0);
153 BOOST_CONTRACT_ASSERT(length() < capacity());
156 BOOST_CONTRACT_OVERRIDES(length
, capacity
, item
, push
, pop
, clear
)
159 explicit vstack(int count
= 10) :
160 boost::contract::constructor_precondition
<vstack
>([&] {
161 BOOST_CONTRACT_ASSERT(count
>= 0);
163 vect_(count
), // OK, executed after precondition so count >= 0.
166 boost::contract::check c
= boost::contract::constructor(this)
168 BOOST_CONTRACT_ASSERT(length() == 0);
169 BOOST_CONTRACT_ASSERT(capacity() == count
);
175 boost::contract::check c
= boost::contract::destructor(this);
178 // Inherited from abstract_stack.
180 virtual int length(boost::contract::virtual_
* v
= 0) const /* override */ {
182 boost::contract::check c
= boost::contract::public_function
<
183 override_length
>(v
, result
, &vstack::length
, this);
184 return result
= len_
;
187 virtual int capacity(boost::contract::virtual_
* v
= 0)
188 const /* override */ {
190 boost::contract::check c
= boost::contract::public_function
<
191 override_capacity
>(v
, result
, &vstack::capacity
, this);
192 return result
= vect_
.size();
195 virtual T
const& item(boost::contract::virtual_
* v
= 0)
196 const /* override */ {
197 boost::optional
<T
const&> result
;
198 boost::contract::check c
= boost::contract::public_function
<
199 override_item
>(v
, result
, &vstack::item
, this);
200 return *(result
= vect_
[len_
- 1]);
203 virtual void push(T
const& value
, boost::contract::virtual_
* v
= 0)
205 boost::contract::check c
= boost::contract::public_function
<
206 override_push
>(v
, &vstack::push
, this, value
);
207 vect_
[len_
++] = value
;
210 virtual T
const& pop(boost::contract::virtual_
* v
= 0) /* override */ {
211 boost::optional
<T
const&> result
;
212 boost::contract::check c
= boost::contract::public_function
<
213 override_pop
>(v
, result
, &vstack::pop
, this);
214 return *(result
= vect_
[--len_
]);
217 virtual void clear(boost::contract::virtual_
* v
= 0) /* override */ {
218 boost::contract::check c
= boost::contract::public_function
<
219 override_clear
>(v
, &vstack::clear
, this);
230 assert(s
.capacity() == 3);
233 assert(s
.length() == 1);
234 assert(s
.pop() == 123);