You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@datasketches.apache.org by al...@apache.org on 2021/10/09 00:01:49 UTC

[datasketches-cpp] 01/01: stop using sstream in to_string method since it does not support passing a custom allocator instance

This is an automated email from the ASF dual-hosted git repository.

alsay pushed a commit to branch no_sstream_in_to_string
in repository https://gitbox.apache.org/repos/asf/datasketches-cpp.git

commit 910987aee38dacdee273d9bf14c5b2fce26ad5cc
Author: AlexanderSaydakov <Al...@users.noreply.github.com>
AuthorDate: Fri Oct 8 17:01:34 2021 -0700

    stop using sstream in to_string method since it does not support passing
    a custom allocator instance
---
 common/include/common_defs.hpp  | 13 +++++++++
 common/test/test_type.hpp       |  6 +++++
 kll/include/kll_sketch.hpp      |  1 +
 kll/include/kll_sketch_impl.hpp | 58 +++++++++++++++++++++--------------------
 4 files changed, 50 insertions(+), 28 deletions(-)

diff --git a/common/include/common_defs.hpp b/common/include/common_defs.hpp
index dadcaac..fa0e204 100644
--- a/common/include/common_defs.hpp
+++ b/common/include/common_defs.hpp
@@ -24,6 +24,7 @@
 #include <string>
 #include <memory>
 #include <iostream>
+#include <sstream>
 
 namespace datasketches {
 
@@ -72,6 +73,18 @@ static inline void write(std::ostream& os, const T* ptr, size_t size_bytes) {
   os.write(reinterpret_cast<const char*>(ptr), size_bytes);
 }
 
+// Default method of obtaining a string representation of an item.
+// This relies on a global std::ostream& operator<<(std::ostream& os, const T&)
+// for compatibility with previous versions of the library.
+// This may change in the next major version.
+template<typename T> struct ostream_based_to_string {
+  std::string operator()(const T& item) const {
+    std::ostringstream s;
+    s << item;
+    return s.str();
+  }
+};
+
 } // namespace
 
 #endif // _COMMON_DEFS_HPP_
diff --git a/common/test/test_type.hpp b/common/test/test_type.hpp
index 18be598..2c94fed 100644
--- a/common/test/test_type.hpp
+++ b/common/test/test_type.hpp
@@ -132,6 +132,12 @@ std::ostream& operator<<(std::ostream& os, const test_type& a) {
   return os;
 }
 
+struct test_type_to_string {
+  std::string operator()(const test_type& a) const {
+    return std::to_string(a.get_value());
+  }
+};
+
 } /* namespace datasketches */
 
 #endif
diff --git a/kll/include/kll_sketch.hpp b/kll/include/kll_sketch.hpp
index fa55520..2b4503c 100644
--- a/kll/include/kll_sketch.hpp
+++ b/kll/include/kll_sketch.hpp
@@ -466,6 +466,7 @@ class kll_sketch {
      * @param print_levels if true include information about levels
      * @param print_items if true include sketch data
      */
+    template<typename ToStr = ostream_based_to_string<T>>
     string<A> to_string(bool print_levels = false, bool print_items = false) const;
 
     class const_iterator;
diff --git a/kll/include/kll_sketch_impl.hpp b/kll/include/kll_sketch_impl.hpp
index 0eb0ae6..f06d9d7 100644
--- a/kll/include/kll_sketch_impl.hpp
+++ b/kll/include/kll_sketch_impl.hpp
@@ -22,7 +22,6 @@
 
 #include <iostream>
 #include <iomanip>
-#include <sstream>
 
 #include "memory_operations.hpp"
 #include "kll_helper.hpp"
@@ -1022,54 +1021,57 @@ void kll_sketch<T, C, S, A>::check_family_id(uint8_t family_id) {
 }
 
 template <typename T, typename C, typename S, typename A>
+template<typename ToStr>
 string<A> kll_sketch<T, C, S, A>::to_string(bool print_levels, bool print_items) const {
-  std::basic_ostringstream<char, std::char_traits<char>, AllocChar<A>> os;
-  os << "### KLL sketch summary:" << std::endl;
-  os << "   K              : " << k_ << std::endl;
-  os << "   min K          : " << min_k_ << std::endl;
-  os << "   M              : " << (unsigned int) m_ << std::endl;
-  os << "   N              : " << n_ << std::endl;
-  os << "   Epsilon        : " << std::setprecision(3) << get_normalized_rank_error(false) * 100 << "%" << std::endl;
-  os << "   Epsilon PMF    : " << get_normalized_rank_error(true) * 100 << "%" << std::endl;
-  os << "   Empty          : " << (is_empty() ? "true" : "false") << std::endl;
-  os << "   Estimation mode: " << (is_estimation_mode() ? "true" : "false") << std::endl;
-  os << "   Levels         : " << (unsigned int) num_levels_ << std::endl;
-  os << "   Sorted         : " << (is_level_zero_sorted_ ? "true" : "false") << std::endl;
-  os << "   Capacity items : " << items_size_ << std::endl;
-  os << "   Retained items : " << get_num_retained() << std::endl;
-  os << "   Storage bytes  : " << get_serialized_size_bytes() << std::endl;
+  string<A> str(allocator_);
+  str.append("### KLL sketch summary:\n");
+  str.append("   K              : ").append(std::to_string(k_)).append("\n");
+  str.append("   min K          : ").append(std::to_string(min_k_)).append("\n");
+  str.append("   M              : ").append(std::to_string(m_)).append("\n");
+  str.append("   N              : ").append(std::to_string(n_)).append("\n");
+  str.append("   Epsilon        : ").append(std::to_string(get_normalized_rank_error(false) * 100)).append("%\n");
+  str.append("   Epsilon PMF    : ").append(std::to_string(get_normalized_rank_error(true) * 100)).append("%\n");
+  str.append("   Empty          : ").append(is_empty() ? "true\n" : "false\n");
+  str.append("   Estimation mode: ").append(is_estimation_mode() ? "true\n" : "false\n");
+  str.append("   Levels         : ").append(std::to_string(num_levels_)).append("\n");
+  str.append("   Sorted         : ").append(is_level_zero_sorted_ ? "true\n" : "false\n");
+  str.append("   Capacity items : ").append(std::to_string(items_size_)).append("\n");
+  str.append("   Retained items : ").append(std::to_string(get_num_retained())).append("\n");
+  str.append("   Storage bytes  : ").append(std::to_string(get_serialized_size_bytes())).append("\n");
   if (!is_empty()) {
-    os << "   Min value      : " << *min_value_ << std::endl;
-    os << "   Max value      : " << *max_value_ << std::endl;
+    str.append("   Min value      : ").append(ToStr()(*min_value_)).append("\n");
+    str.append("   Max value      : ").append(ToStr()(*max_value_)).append("\n");
   }
-  os << "### End sketch summary" << std::endl;
+  str.append("### End sketch summary\n");
 
   if (print_levels) {
-    os << "### KLL sketch levels:" << std::endl;
-    os << "   index: nominal capacity, actual size" << std::endl;
+    str.append("### KLL sketch levels:\n");
+    str.append("   index: nominal capacity, actual size\n");
     for (uint8_t i = 0; i < num_levels_; i++) {
-      os << "   " << (unsigned int) i << ": " << kll_helper::level_capacity(k_, num_levels_, i, m_) << ", " << safe_level_size(i) << std::endl;
+      auto level_capacity = kll_helper::level_capacity(k_, num_levels_, i, m_);
+      str.append("   ").append(std::to_string(i)).append(": ").append(std::to_string(level_capacity))
+          .append(", ").append(std::to_string(safe_level_size(i))).append("\n");
     }
-    os << "### End sketch levels" << std::endl;
+    str.append("### End sketch levels\n");
   }
 
   if (print_items) {
-    os << "### KLL sketch data:" << std::endl;
+    str.append("### KLL sketch data:\n");
     uint8_t level = 0;
     while (level < num_levels_) {
       const uint32_t from_index = levels_[level];
       const uint32_t to_index = levels_[level + 1]; // exclusive
       if (from_index < to_index) {
-        os << " level " << (unsigned int) level << ":" << std::endl;
+        str.append(" level ").append(std::to_string(level)).append(":\n");
       }
       for (uint32_t i = from_index; i < to_index; i++) {
-        os << "   " << items_[i] << std::endl;
+        str.append("   ").append(ToStr()(items_[i])).append("\n");
       }
       level++;
     }
-    os << "### End sketch data" << std::endl;
+    str.append("### End sketch data\n");
   }
-  return os.str();
+  return str;
 }
 
 template <typename T, typename C, typename S, typename A>

---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscribe@datasketches.apache.org
For additional commands, e-mail: commits-help@datasketches.apache.org