[Groonga-commit] groonga/grnxx at 2a25af7 [master] Prepare for sorting.

Back to archive index

susumu.yata null+****@clear*****
Thu Jul 24 17:59:20 JST 2014


susumu.yata	2014-07-24 17:59:20 +0900 (Thu, 24 Jul 2014)

  New Revision: 2a25af74f61f52783b657d7e8531de9e92f00e23
  https://github.com/groonga/grnxx/commit/2a25af74f61f52783b657d7e8531de9e92f00e23

  Message:
    Prepare for sorting.

  Modified files:
    include/grnxx/order.hpp
    include/grnxx/sorter.hpp
    include/grnxx/types.hpp
    lib/grnxx/sorter.cpp

  Modified: include/grnxx/order.hpp (+1 -1)
===================================================================
--- include/grnxx/order.hpp    2014-07-24 11:17:30 +0900 (f5c7f1b)
+++ include/grnxx/order.hpp    2014-07-24 17:59:20 +0900 (348adbb)
@@ -31,7 +31,7 @@ class OrderSet {
   // Return the "i"-th sort condition.
   //
   // If "i" is invalid, the result is undefined.
-  const Order &get(Int i) const {
+  Order &get(Int i) {
     return orders_[i];
   }
 

  Modified: include/grnxx/sorter.hpp (+1 -0)
===================================================================
--- include/grnxx/sorter.hpp    2014-07-24 11:17:30 +0900 (580fd48)
+++ include/grnxx/sorter.hpp    2014-07-24 17:59:20 +0900 (3e4b886)
@@ -56,6 +56,7 @@ class Sorter {
 
  private:
   RecordSet *record_set_;
+  unique_ptr<SorterNode> head_;
 
   Sorter();
 };

  Modified: include/grnxx/types.hpp (+1 -0)
===================================================================
--- include/grnxx/types.hpp    2014-07-24 11:17:30 +0900 (aada258)
+++ include/grnxx/types.hpp    2014-07-24 17:59:20 +0900 (0ffab64)
@@ -409,6 +409,7 @@ class ExpressionNode;
 class ExpressionBuilder;
 class OrderSet;
 class OrderSetBuilder;
+class SorterNode;
 class Sorter;
 
 }  // namespace grnxx

  Modified: lib/grnxx/sorter.cpp (+147 -5)
===================================================================
--- lib/grnxx/sorter.cpp    2014-07-24 11:17:30 +0900 (92a88b9)
+++ lib/grnxx/sorter.cpp    2014-07-24 17:59:20 +0900 (8e3f48f)
@@ -1,14 +1,145 @@
 #include "grnxx/sorter.hpp"
 
 #include "grnxx/error.hpp"
+#include "grnxx/expression.hpp"
+#include "grnxx/order.hpp"
+#include "grnxx/record.hpp"
 
 namespace grnxx {
+
+class SorterNode {
+ public:
+  static unique_ptr<SorterNode> create(Error *error, Order &&order);
+
+  SorterNode() : next_(nullptr) {}
+  virtual ~SorterNode() {}
+
+  // Return the next node.
+  SorterNode *next() const {
+    return next_.get();
+  }
+  // Set the next node.
+  void set_next(unique_ptr<SorterNode> &&next) {
+    next_ = std::move(next);
+  }
+
+  // Sort records in [begin, end).
+  //
+  // On success, returns true.
+  // On failure, returns false and stores error information into "*error" if
+  // "error" != nullptr.
+  virtual bool sort(Error *error,
+                    RecordSet *record_set,
+                    Int begin,
+                    Int end) = 0;
+
+ private:
+  unique_ptr<SorterNode> next_;
+};
+
 namespace {
 
-// TODO
+template <typename T>
+struct RegularComparer {
+  using Value = T;
+  bool operator()(T lhs, T rhs) const {
+    return lhs < rhs;
+  }
+};
+
+template <typename T>
+struct ReverseComparer {
+  using Value = T;
+  bool operator()(T lhs, T rhs) const {
+    return rhs < lhs;
+  }
+};
+
+template <typename T>
+class Node : public SorterNode {
+ public:
+  using Value = typename T::Value;
+
+  Node(Order &&order) : SorterNode(), order_(std::move(order)) {}
+  ~Node() {}
+
+  bool sort(Error *error, RecordSet *record_set, Int begin, Int end);
+
+ private:
+  Order order_;
+  std::vector<Value> values_;
+
+  // TODO: A pointer to records is not available.
+//  void quick_sort(Record *records, Value *values, Int size,
+//                  Int begin, Int end);
+//  void insertion_sort(Record *records, Value *values, Int size);
+//  void move_pivot_first(Record *records, Value *values, Int size);
+};
+
+template <typename T>
+bool Node<T>::sort(Error *error, RecordSet *record_set, Int begin, Int end) {
+  return false;
+}
 
 }  // namespace
 
+unique_ptr<SorterNode> SorterNode::create(Error *error, Order &&order) {
+  unique_ptr<SorterNode> node;
+  switch (order.expression->data_type()) {
+    // TODO: Bool type does not support pointer.
+//    case BOOL_DATA: {
+//      node.reset(new (nothrow) Node<Bool>(std::move(order)));
+//      break;
+//    }
+    case INT_DATA: {
+      if (order.type == REGULAR_ORDER) {
+        node.reset(new (nothrow) Node<RegularComparer<Int>>(std::move(order)));
+      } else {
+        node.reset(new (nothrow) Node<ReverseComparer<Int>>(std::move(order)));
+      }
+      break;
+    }
+    case FLOAT_DATA: {
+      if (order.type == REGULAR_ORDER) {
+        node.reset(
+            new (nothrow) Node<RegularComparer<Float>>(std::move(order)));
+      } else {
+        node.reset(
+            new (nothrow) Node<ReverseComparer<Float>>(std::move(order)));
+      }
+      break;
+    }
+    case TIME_DATA: {
+      if (order.type == REGULAR_ORDER) {
+        node.reset(
+            new (nothrow) Node<RegularComparer<Time>>(std::move(order)));
+      } else {
+        node.reset(
+            new (nothrow) Node<ReverseComparer<Time>>(std::move(order)));
+      }
+      break;
+    }
+    case TEXT_DATA: {
+      if (order.type == REGULAR_ORDER) {
+        node.reset(
+            new (nothrow) Node<RegularComparer<Text>>(std::move(order)));
+      } else {
+        node.reset(
+            new (nothrow) Node<ReverseComparer<Text>>(std::move(order)));
+      }
+      break;
+    }
+    default: {
+      GRNXX_ERROR_SET(error, NOT_SUPPORTED_YET, "Not supported yet");
+      return nullptr;
+    }
+  }
+  if (!node) {
+    GRNXX_ERROR_SET(error, NO_MEMORY, "Memory allocation failed");
+  }
+  return node;
+}
+
 Sorter::~Sorter() {}
 
 unique_ptr<Sorter> Sorter::create(
@@ -20,6 +151,16 @@ unique_ptr<Sorter> Sorter::create(
     GRNXX_ERROR_SET(error, NO_MEMORY, "Memory allocation failed");
     return nullptr;
   }
+  for (Int i = order_set->size() - 1; i >= 0; --i) {
+    unique_ptr<SorterNode> node(
+        SorterNode::create(error, std::move(order_set->get(i))));
+    if (!node) {
+      return nullptr;
+    }
+    node->set_next(std::move(sorter->head_));
+    sorter->head_ = std::move(node);
+  }
+  order_set.reset();
   return sorter;
 }
 
@@ -38,15 +179,16 @@ bool Sorter::finish(Error *error) {
     // Nothing to do.
     return true;
   }
-  // TODO: Sorting is not supported yet.
-  GRNXX_ERROR_SET(error, NOT_SUPPORTED_YET, "Not supported yet");
-  return false;
+  if (record_set_->size() <= 1) {
+    return true;
+  }
+  return head_->sort(error, record_set_, 0, record_set_->size());
 }
 
 bool Sorter::sort(Error *error, RecordSet *record_set) {
   return reset(error, record_set) && finish(error);
 }
 
-Sorter::Sorter() : record_set_(nullptr) {}
+Sorter::Sorter() : record_set_(nullptr), head_() {}
 
 }  // namespace grnxx
-------------- next part --------------
HTML����������������������������...
Download 



More information about the Groonga-commit mailing list
Back to archive index