Direct-BT  2.3.1
Direct-BT - Direct Bluetooth Programming.
test_cow_darray_01.cpp
Go to the documentation of this file.
1 /*
2  * Author: Sven Gothel <sgothel@jausoft.com>
3  * Copyright (c) 2020 Gothel Software e.K.
4  *
5  * Permission is hereby granted, free of charge, to any person obtaining
6  * a copy of this software and associated documentation files (the
7  * "Software"), to deal in the Software without restriction, including
8  * without limitation the rights to use, copy, modify, merge, publish,
9  * distribute, sublicense, and/or sell copies of the Software, and to
10  * permit persons to whom the Software is furnished to do so, subject to
11  * the following conditions:
12  *
13  * The above copyright notice and this permission notice shall be
14  * included in all copies or substantial portions of the Software.
15  *
16  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
17  * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
18  * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
19  * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
20  * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
21  * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
22  * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
23  */
24 #include <iostream>
25 #include <cassert>
26 #include <cinttypes>
27 #include <cstring>
28 #include <random>
29 #include <vector>
30 
31 #define CATCH_CONFIG_RUNNER
32 // #define CATCH_CONFIG_MAIN
33 #include <catch2/catch_amalgamated.hpp>
34 #include <jau/test/catch2_ext.hpp>
35 
36 #include "test_datatype01.hpp"
37 
38 #include "test_datatype02.hpp"
39 
40 #include <jau/basic_algos.hpp>
41 #include <jau/basic_types.hpp>
42 #include <jau/darray.hpp>
43 #include <jau/cow_darray.hpp>
44 #include <jau/cow_vector.hpp>
46 #include <jau/callocator.hpp>
48 
49 /**
50  * Test general use of jau::darray, jau::cow_darray and jau::cow_vector.
51  */
52 using namespace jau;
53 
54 /**********************************************************************************************************************************************/
55 /**********************************************************************************************************************************************/
56 /**********************************************************************************************************************************************/
57 /**********************************************************************************************************************************************/
58 /**********************************************************************************************************************************************/
59 
60 TEST_CASE( "JAU DArray Test 01 - jau::darray initializer list", "[datatype][jau][darray]" ) {
61  int i = 0;
63  (void)ml;
64  // printf("XX: %s\n\n", ml->toString().c_str());
65  ++i;
66  });
67  REQUIRE(3 == i);
68 }
69 
70 /**********************************************************************************************************************************************/
71 /**********************************************************************************************************************************************/
72 /**********************************************************************************************************************************************/
73 /**********************************************************************************************************************************************/
74 /**********************************************************************************************************************************************/
75 
76 template<class Payload>
78 // JAU_TYPENAME_CUE_ALL(SharedPayloadListMemMove)
79 
80 template<class Payload>
82 // JAU_TYPENAME_CUE_ALL(SharedPayloadListDefault)
83 
84 template<class Payload>
86  int name;
88 
89  std::string toString() const noexcept {
90  std::string res = "NSPL-Default-"+std::to_string(name)+"[sz"+std::to_string(payload.size())+": ";
91  int i=0;
92  jau::for_each(payload.cbegin(), payload.cend(), [&](const std::shared_ptr<Payload>& e) {
93  if(0<i) {
94  res += ", ";
95  }
96  res += "["+jau::to_string(e)+"]";
97  ++i;
98  } );
99  res += "]";
100  return res;
101  }
102 };
103 // JAU_TYPENAME_CUE_ALL(NamedSharedPayloadListDefault)
104 
105 template<class Payload>
107  int name;
109 
110  std::string toString() const noexcept {
111  std::string res = "NSPL-MemMove-"+std::to_string(name)+"[sz"+std::to_string(payload.size())+": ";
112  int i=0;
113  jau::for_each(payload.cbegin(), payload.cend(), [&](const std::shared_ptr<Payload>& e) {
114  if(0<i) {
115  res += ", ";
116  }
117  res += "["+jau::to_string(e)+"]";
118  ++i;
119  } );
120  res += "]";
121  return res;
122  }
123 };
124 // JAU_TYPENAME_CUE_ALL(NamedSharedPayloadListMemMove)
125 
126 template<class Payload>
127 using PayloadListMemMove = jau::darray<Payload, jau::callocator<Payload>, jau::nsize_t, true /* use_memmove */, true /* use_realloc */>;
128 // JAU_TYPENAME_CUE_ALL(PayloadListMemMove)
129 
130 template<class Payload>
132 // JAU_TYPENAME_CUE_ALL(PayloadListDefault)
133 
134 template<class Payload>
136  int name;
138 
139  std::string toString() const noexcept {
140  std::string res = "NPL-Default-"+std::to_string(name)+"[sz"+std::to_string(payload.size())+": ";
141  int i=0;
142  jau::for_each(payload.cbegin(), payload.cend(), [&](const typename PayloadListDefault<Payload>::value_type & e) {
143  if(0<i) {
144  res += ", ";
145  }
146  res += "["+jau::to_string(e)+"]";
147  ++i;
148  } );
149  res += "]";
150  return res;
151  }
152 };
153 // JAU_TYPENAME_CUE_ALL(NamedPayloadListDefault)
154 
155 template<class Payload>
157  int name;
159 
160  std::string toString() const noexcept {
161  std::string res = "NPL-MemMove-"+std::to_string(name)+"[sz"+std::to_string(payload.size())+": ";
162  int i=0;
163  jau::for_each(payload.cbegin(), payload.cend(), [&](const Payload& e) {
164  if(0<i) {
165  res += ", ";
166  }
167  res += "["+jau::to_string(e)+"]";
168  ++i;
169  } );
170  res += "]";
171  return res;
172  }
173 };
174 // JAU_TYPENAME_CUE_ALL(NamedPayloadListMemMove)
175 
176 template<class Payload>
179  int i=0;
180  for(i=0; i<2; i++) {
181  std::shared_ptr<Payload> sp(std::make_shared<Payload>( name+i )); // copy-elision + make_shared in-place
182  data.push_back( sp );
183  }
184  for(i=2; i<4; i++) {
185  std::shared_ptr<Payload> sp(new Payload( name+i )); // double malloc: 1 Payload, 2 shared_ptr
186  data.push_back( std::move( sp ) ); // move the less efficient into
187  }
188  return NamedSharedPayloadListDefault<Payload>{name, data};
189 }
190 template<class Payload>
192  printf("XXX1: %s\n", src.toString().c_str());
193  src.payload.pop_back();
194  src.payload.erase(src.payload.cbegin());
195  printf("XXX2: %s\n", src.toString().c_str());
196  return src;
197 }
198 
199 template<class Payload>
202  int i=0;
203  for(i=0; i<2; i++) {
204  std::shared_ptr<Payload> sp(std::make_shared<Payload>( name+i )); // copy-elision + make_shared in-place
205  data.push_back( sp );
206  }
207  for(i=2; i<4; i++) {
208  std::shared_ptr<Payload> sp(new Payload( name+i )); // double malloc: 1 Payload, 2 shared_ptr
209  data.push_back( std::move( sp ) ); // move the less efficient into
210  }
211  return NamedSharedPayloadListMemMove<Payload>{name, data};
212 }
213 template<class Payload>
216  int i=0;
217  for(i=0; i<2; i++) {
218  Payload sp( name+i ); // copy-elision
219  data.push_back( sp );
220  }
221  for(i=2; i<4; i++) {
222  Payload sp( name+i );
223  data.push_back( std::move( sp ) ); // move the less efficient into
224  }
225  return NamedPayloadListDefault<Payload>{name, data};
226 }
227 template<class Payload>
230  int i=0;
231  for(i=0; i<2; i++) {
232  Payload sp( name+i ); // copy-elision
233  data.push_back( sp );
234  }
235  for(i=2; i<4; i++) {
236  Payload sp( name+i );
237  data.push_back( std::move( sp ) ); // move the less efficient into
238  }
239  return NamedPayloadListMemMove<Payload>{name, data};
240 }
241 
242 JAU_TYPENAME_CUE_ALL(std::shared_ptr<Addr48Bit>)
244 JAU_TYPENAME_CUE_ALL(jau::darray<std::shared_ptr<Addr48Bit>>)
245 
246 JAU_TYPENAME_CUE_ALL(std::shared_ptr<DataType01>)
248 JAU_TYPENAME_CUE_ALL(jau::darray<std::shared_ptr<DataType01>>)
249 
250 #define CHECK_TRAITS 0
251 
252 template< class Cont >
253 static void print_container_info(const std::string& type_id, const Cont &c,
254  std::enable_if_t< jau::is_darray_type<Cont>::value, bool> = true )
255 {
256  printf("\nContainer Type %s (a darray, a cow %d):\n - Uses memcpy %d (trivially_copyable %d); realloc %d; base_of jau::callocator %d; size %d bytes\n",
257  type_id.c_str(), jau::is_cow_type<Cont>::value,
258  Cont::uses_memmove,
259  std::is_trivially_copyable<typename Cont::value_type>::value,
260  Cont::uses_realloc,
261  std::is_base_of<jau::callocator<typename Cont::value_type>, typename Cont::allocator_type>::value,
262  (int)sizeof(c));
263 }
264 
265 template<class Cont>
266 static void print_container_info(const std::string& type_id, const Cont &c,
267  std::enable_if_t< !jau::is_darray_type<Cont>::value, bool> = true )
268 {
269  printf("\nContainer Type %s (!darray, a cow %d); size %d bytes\n",
270  type_id.c_str(), jau::is_cow_type<Cont>::value, (int)sizeof(c));
271 }
272 
273 
274 template<class Payload>
275 static void testDArrayValueType(const std::string& type_id) {
276  {
277  // jau::type_cue<Payload>::print(type_id, jau::TypeTraitGroup::ALL);
278  // jau::type_cue<std::shared_ptr<Payload>>::print("std::shared_ptr<"+type_id+">", jau::TypeTraitGroup::ALL);
279  }
280  {
281 #if CHECK_TRAITS
282  CHECK( true == std::is_base_of<jau::callocator<Payload>, jau::callocator<Payload>>::value);
284  CHECK( true == std::is_trivially_copyable<Payload>::value);
286 #endif
287 
288  NamedPayloadListDefault<Payload> data = makeNamedPayloadListDefault<Payload>(1);
289  print_container_info("NamedPayloadListDefault<"+type_id+">", data.payload);
290 
292  data2.payload.erase(data2.payload.cbegin());
293 
295  data3.payload.erase(data3.payload.begin(), data3.payload.cbegin()+data3.payload.size()/2);
296 
297  NamedPayloadListDefault<Payload> data8 = makeNamedPayloadListDefault<Payload>(8);
298  data8.payload.insert(data8.payload.begin(), data.payload.cbegin(), data.payload.cend());
299 
300  printf("COPY-0: %s\n\n", data.toString().c_str());
301  printf("COPY-1: %s\n\n", data2.toString().c_str());
302  printf("COPY-2: %s\n\n", data3.toString().c_str());
303  printf("COPY+2: %s\n\n", data8.toString().c_str());
304  }
305  {
306 #if CHECK_TRAITS
307  CHECK( true == std::is_base_of<jau::callocator<Payload>, jau::callocator<Payload>>::value);
309  CHECK( true == std::is_trivially_copyable<Payload>::value);
311 #endif
312 
313  NamedPayloadListMemMove<Payload> data = makeNamedPayloadListMemMove<Payload>(1);
314  print_container_info("NamedPayloadListMemMove<"+type_id+">", data.payload);
315 
317  data2.payload.erase(data2.payload.cbegin());
318 
320  data3.payload.erase(data3.payload.begin(), data3.payload.cbegin()+data3.payload.size()/2);
321 
322  NamedPayloadListMemMove<Payload> data8 = makeNamedPayloadListMemMove<Payload>(8);
323  data8.payload.insert(data8.payload.begin(), data.payload.cbegin(), data.payload.cend());
324 
325  printf("COPY-0: %s\n\n", data.toString().c_str());
326  printf("COPY-1: %s\n\n", data2.toString().c_str());
327  printf("COPY-2: %s\n\n", data3.toString().c_str());
328  printf("COPY+2: %s\n\n", data8.toString().c_str());
329  }
330  {
331 #if CHECK_TRAITS
332  CHECK( true == std::is_base_of<jau::callocator<std::shared_ptr<Payload>>, jau::callocator<std::shared_ptr<Payload>>>::value);
334  CHECK( true == std::is_trivially_copyable<std::shared_ptr<Payload>>::value);
336 #endif
337 
338  NamedSharedPayloadListDefault<Payload> data = makeNamedSharedPayloadListDefault<Payload>(1);
339  print_container_info("NamedSharedPayloadListDefault<"+type_id+">", data.payload);
340 
342  data2.payload.erase(data2.payload.cbegin());
343 
345  data3.payload.erase(data3.payload.begin(), data3.payload.cbegin()+data3.payload.size()/2);
346 
347  NamedSharedPayloadListDefault<Payload> data8 = makeNamedSharedPayloadListDefault<Payload>(8);
348  data8.payload.insert(data8.payload.begin(), data.payload.cbegin(), data.payload.cend());
349 
350  printf("COPY-0: %s\n\n", data.toString().c_str());
351  printf("COPY-1: %s\n\n", data2.toString().c_str());
352  printf("COPY-2: %s\n\n", data3.toString().c_str());
353  printf("COPY+2: %s\n\n", data8.toString().c_str());
354 
356  printf("MODI+2-2: %s\n\n", data8_mod.toString().c_str());
357 
358  struct Holder {
360  NamedSharedPayloadListDefault<Payload> & get_ref() { return lala; }
361  NamedSharedPayloadListDefault<Payload> & get_ref2() { lala.payload.pop_back(); return lala; }
362  NamedSharedPayloadListDefault<Payload> get_copy() { return lala; }
363  };
364  Holder holder{ data };
365  NamedSharedPayloadListDefault<Payload> & r1r1 = holder.get_ref();
366  printf("R1R1: %s\n\n", r1r1.toString().c_str());
367 
368  NamedSharedPayloadListDefault<Payload> r2c1 = holder.get_ref();
369  printf("R1C1: %s\n\n", r2c1.toString().c_str());
370 
371  NamedSharedPayloadListDefault<Payload> c1c2 = holder.get_copy();
372  printf("C1C2: %s\n\n", c1c2.toString().c_str());
373 
374  r1r1 = holder.get_ref2();
375  printf("R2R2: %s\n\n", r1r1.toString().c_str());
376  }
377  {
378 #if CHECK_TRAITS
379  CHECK( true == std::is_base_of<jau::callocator<std::shared_ptr<Payload>>, jau::callocator<std::shared_ptr<Payload>>>::value);
381  CHECK( true == std::is_trivially_copyable<std::shared_ptr<Payload>>::value);
383 #endif
384 
385  NamedSharedPayloadListMemMove<Payload> data = makeNamedSharedPayloadListMemMove<Payload>(1);
386  print_container_info("NamedSharedPayloadListMemMove<"+type_id+">", data.payload);
387 
389  data2.payload.erase(data2.payload.cbegin());
390 
392  data3.payload.erase(data3.payload.begin(), data3.payload.cbegin()+data3.payload.size()/2);
393 
394  NamedSharedPayloadListMemMove<Payload> data8 = makeNamedSharedPayloadListMemMove<Payload>(8);
395  data8.payload.insert(data8.payload.begin(), data.payload.cbegin(), data.payload.cend());
396 
397  printf("COPY-0: %s\n\n", data.toString().c_str());
398  printf("COPY-1: %s\n\n", data2.toString().c_str());
399  printf("COPY-2: %s\n\n", data3.toString().c_str());
400  printf("COPY+2: %s\n\n", data8.toString().c_str());
401  }
402 }
403 
405  return *GATT_SERVICES[i];
406 }
407 
409 #if CHECK_TRAITS
411  CHECK( true == GattCharacteristicSpecList::uses_realloc);
412 
413  CHECK( true == GattCharacteristicSpecList::uses_memmove);
414  CHECK( true == std::is_trivially_copyable<GattCharacteristicSpec>::value);
415 #endif
416 
418  print_container_info("darray<GattCharacteristicSpec>", gatt2.characteristics);
419 
421 
422  GattServiceCharacteristic gatt2b = gatt2;
423  gatt2b.characteristics.erase(gatt2b.characteristics.cbegin());
424 
425  GattServiceCharacteristic gatt2c(gatt2);
426  gatt2c.characteristics.erase(gatt2c.characteristics.cbegin());
427 
428  printf("COPY0-1: %s\n\n", gatt2.toString().c_str());
429  printf("COPY1-2: %s\n\n", gatt2b.toString().c_str());
430  printf("COPY2-3: %s\n\n", gatt2c.toString().c_str());
431 }
432 
433 TEST_CASE( "JAU DArray Test 02 - jau::darray value_type behavior (type traits)", "[datatype][jau][darray]" ) {
434  testDArrayValueType<uint64_t>("uint64_t");
435  testDArrayValueType<Addr48Bit>("Addr48Bit");
436  testDArrayValueType<DataType01>("DataType01");
438 }
439 
440 /**********************************************************************************************************************************************/
441 /**********************************************************************************************************************************************/
442 /**********************************************************************************************************************************************/
443 /**********************************************************************************************************************************************/
444 /**********************************************************************************************************************************************/
445 
GattServiceCharacteristic::toString
std::string toString() const noexcept
Definition: test_datatype02.hpp:442
callocator.hpp
NamedPayloadListDefault::name
int name
Definition: test_cow_darray_01.cpp:136
darray.hpp
NamedPayloadListMemMove
Definition: test_cow_darray_01.cpp:156
test_datatype02.hpp
TEST_CASE
TEST_CASE("JAU DArray Test 01 - jau::darray initializer list", "[datatype][jau][darray]")
Definition: test_cow_darray_01.cpp:60
counting_callocator.hpp
basic_algos.hpp
NamedSharedPayloadListDefault::toString
std::string toString() const noexcept
Definition: test_cow_darray_01.cpp:89
jau::is_darray_type
template< class T > is_darray_type<T>::value compile-time Type Trait, determining whether the given t...
Definition: darray.hpp:1206
NamedSharedPayloadListMemMove::name
int name
Definition: test_cow_darray_01.cpp:107
makeNamedPayloadListMemMove
static NamedPayloadListMemMove< Payload > makeNamedPayloadListMemMove(int name)
Definition: test_cow_darray_01.cpp:228
jau::darray::cbegin
constexpr const_iterator cbegin() const noexcept
Definition: darray.hpp:610
jau::for_each
constexpr UnaryFunction for_each(InputIt first, InputIt last, UnaryFunction f)
Like std::for_each() of 'algorithm'.
Definition: basic_algos.hpp:163
jau
Definition: basic_algos.hpp:34
NamedSharedPayloadListDefault
Definition: test_cow_darray_01.cpp:85
jau::is_cow_type
template< class T > is_cow_type<T>::value compile-time Type Trait, determining whether the given temp...
Definition: cow_iterator.hpp:1039
jau::to_string
PRAGMA_DISABLE_WARNING_POP constexpr_cxx20 std::string to_string(const endian &v) noexcept
Return std::string representation of the given jau::endian.
Definition: byte_util.hpp:198
jau::darray
Implementation of a dynamic linear array storage, aka vector.
Definition: darray.hpp:102
jau::darray::push_back
constexpr void push_back(const value_type &x)
Like std::vector::push_back(), copy.
Definition: darray.hpp:991
cow_darray.hpp
test_datatype01.hpp
makeNamedPayloadListDefault
static NamedPayloadListDefault< Payload > makeNamedPayloadListDefault(int name)
Definition: test_cow_darray_01.cpp:214
NamedPayloadListMemMove::payload
PayloadListMemMove< Payload > payload
Definition: test_cow_darray_01.cpp:158
cow_vector.hpp
GATT_SERVICES
const jau::darray< const GattServiceCharacteristic * > GATT_SERVICES
Definition: test_datatype02.hpp:334
returnGattSrvcChar
static GattServiceCharacteristic returnGattSrvcChar(int i)
Definition: test_cow_darray_01.cpp:404
jau::darray< Payload >::value_type
Payload value_type
Definition: darray.hpp:113
JAU_TYPENAME_CUE_ALL
#define JAU_TYPENAME_CUE_ALL(A)
Definition: type_traits_queries.hpp:223
NamedPayloadListMemMove::name
int name
Definition: test_cow_darray_01.cpp:157
NamedPayloadListDefault::toString
std::string toString() const noexcept
Definition: test_cow_darray_01.cpp:139
NamedSharedPayloadListMemMove
Definition: test_cow_darray_01.cpp:106
jau::darray::size
constexpr size_type size() const noexcept
Like std::vector::size().
Definition: darray.hpp:668
counting_allocator.hpp
NamedSharedPayloadListDefault::name
int name
Definition: test_cow_darray_01.cpp:86
makeNamedSharedPayloadListMemMove
static NamedSharedPayloadListMemMove< Payload > makeNamedSharedPayloadListMemMove(int name)
Definition: test_cow_darray_01.cpp:200
NamedSharedPayloadListMemMove::payload
SharedPayloadListMemMove< Payload > payload
Definition: test_cow_darray_01.cpp:108
NamedPayloadListDefault
Definition: test_cow_darray_01.cpp:135
GattServiceCharacteristic::characteristics
jau::darray< GattCharacteristicSpec > characteristics
Definition: test_datatype02.hpp:174
NamedPayloadListDefault::payload
PayloadListDefault< Payload > payload
Definition: test_cow_darray_01.cpp:137
NamedPayloadListMemMove::toString
std::string toString() const noexcept
Definition: test_cow_darray_01.cpp:160
NamedSharedPayloadListDefault::payload
SharedPayloadListDefault< Payload > payload
Definition: test_cow_darray_01.cpp:87
jau::nsize_t
uint_fast32_t nsize_t
Natural 'size_t' alternative using uint_fast32_t as its natural sized type.
Definition: int_types.hpp:44
testDArrayGattServiceCharacteristic
static void testDArrayGattServiceCharacteristic()
Definition: test_cow_darray_01.cpp:408
DataType01
Definition: test_datatype01.hpp:141
jau::callocator
A simple allocator using POSIX C functions: ::malloc(), ::free() and ::realloc().
Definition: callocator.hpp:53
testDArrayValueType
static void testDArrayValueType(const std::string &type_id)
Definition: test_cow_darray_01.cpp:275
print_container_info
static void print_container_info(const std::string &type_id, const Cont &c, std::enable_if_t< jau::is_darray_type< Cont >::value, bool >=true)
Definition: test_cow_darray_01.cpp:253
modifyCopyOfNamedSharedPayloadListDefault
static NamedSharedPayloadListDefault< Payload > modifyCopyOfNamedSharedPayloadListDefault(NamedSharedPayloadListDefault< Payload > src)
Definition: test_cow_darray_01.cpp:191
makeNamedSharedPayloadListDefault
static NamedSharedPayloadListDefault< Payload > makeNamedSharedPayloadListDefault(int name)
Definition: test_cow_darray_01.cpp:177
basic_types.hpp
catch2_ext.hpp
GattServiceCharacteristic
Definition: test_datatype02.hpp:172
jau::darray::erase
constexpr iterator erase(const_iterator pos)
Like std::vector::erase(), removes the elements at pos.
Definition: darray.hpp:832
NamedSharedPayloadListMemMove::toString
std::string toString() const noexcept
Definition: test_cow_darray_01.cpp:110
jau::darray::cend
constexpr const_iterator cend() const noexcept
Definition: darray.hpp:616