You've already forked mariadb-columnstore-engine
							
							
				mirror of
				https://github.com/mariadb-corporation/mariadb-columnstore-engine.git
				synced 2025-10-30 07:25:34 +03:00 
			
		
		
		
	
		
			
				
	
	
		
			274 lines
		
	
	
		
			7.0 KiB
		
	
	
	
		
			C++
		
	
	
	
	
	
			
		
		
	
	
			274 lines
		
	
	
		
			7.0 KiB
		
	
	
	
		
			C++
		
	
	
	
	
	
| /* Copyright (C) 2014 InfiniDB, Inc.
 | |
| 
 | |
|    This program is free software; you can redistribute it and/or
 | |
|    modify it under the terms of the GNU General Public License
 | |
|    as published by the Free Software Foundation; version 2 of
 | |
|    the License.
 | |
| 
 | |
|    This program is distributed in the hope that it will be useful,
 | |
|    but WITHOUT ANY WARRANTY; without even the implied warranty of
 | |
|    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 | |
|    GNU General Public License for more details.
 | |
| 
 | |
|    You should have received a copy of the GNU General Public License
 | |
|    along with this program; if not, write to the Free Software
 | |
|    Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
 | |
|    MA 02110-1301, USA. */
 | |
| 
 | |
| /******************************************************************************
 | |
|  * $Id: datalistimpl.h 9655 2013-06-25 23:08:13Z xlou $
 | |
|  *
 | |
|  *****************************************************************************/
 | |
| 
 | |
| /** @file
 | |
|  * class XXX interface
 | |
|  */
 | |
| 
 | |
| #include <vector>
 | |
| #include <set>
 | |
| #include <typeinfo>
 | |
| #include <stdexcept>
 | |
| #include <cassert>
 | |
| #include <sstream>
 | |
| 
 | |
| #include "datalist.h"
 | |
| 
 | |
| #pragma once
 | |
| 
 | |
| namespace joblist
 | |
| {
 | |
| /** @brief class DataListImpl
 | |
|  *
 | |
|  */
 | |
| template <typename container_t, typename element_t>
 | |
| class DataListImpl : public DataList<element_t>
 | |
| {
 | |
|  public:
 | |
|   explicit DataListImpl(uint32_t numConsumers);
 | |
|   DataListImpl(const DataListImpl& dl);
 | |
|   ~DataListImpl() override;
 | |
| 
 | |
|   DataListImpl& operator=(const DataListImpl& dl);
 | |
| 
 | |
|   // derived classes need to lock around these fcns
 | |
|   void insert(const element_t& e) override;
 | |
|   void insert(const std::vector<element_t>& v) override;
 | |
|   uint64_t getIterator() override;
 | |
|   bool next(uint64_t it, element_t* e) override;
 | |
| 
 | |
|   virtual void setNumConsumers(uint32_t);
 | |
|   virtual uint32_t getNumConsumers() const;
 | |
|   void resetNumConsumers(uint32_t numConsumers);
 | |
| 
 | |
|  protected:
 | |
|   bool endOfData(uint64_t id) const;
 | |
|   void eraseUpTo(uint64_t id);
 | |
|   void reset();
 | |
|   virtual void shrink();
 | |
|   typename container_t::iterator iInsert(const element_t& e);
 | |
| 
 | |
|   container_t* c;
 | |
|   typename container_t::iterator* cIterators;
 | |
|   uint64_t numConsumers;
 | |
|   uint64_t itIndex;
 | |
| 
 | |
|  private:
 | |
|   explicit DataListImpl();
 | |
| };
 | |
| 
 | |
| template <typename container_t, typename element_t>
 | |
| DataListImpl<container_t, element_t>::DataListImpl()
 | |
|  : DataList<element_t>(), c(0), cIterators(0), numConsumers(0), itIndex(0)
 | |
| {
 | |
| }
 | |
| 
 | |
| template <typename container_t, typename element_t>
 | |
| void DataListImpl<container_t, element_t>::setNumConsumers(uint32_t nc)
 | |
| {
 | |
|   resetNumConsumers(nc);
 | |
| }
 | |
| 
 | |
| template <typename container_t, typename element_t>
 | |
| uint32_t DataListImpl<container_t, element_t>::getNumConsumers() const
 | |
| {
 | |
|   return numConsumers;
 | |
| }
 | |
| 
 | |
| template <typename container_t, typename element_t>
 | |
| void DataListImpl<container_t, element_t>::resetNumConsumers(uint32_t nc)
 | |
| {
 | |
|   if (itIndex != 0)
 | |
|     throw std::logic_error(
 | |
|         "DataListImpl::resetNumConsumers(): attempt to change numConsumers "
 | |
|         "after iterators have been issued");
 | |
| 
 | |
|   uint32_t i;
 | |
| 
 | |
|   numConsumers = nc;
 | |
|   delete[] cIterators;
 | |
|   cIterators = new typename container_t::iterator[numConsumers];
 | |
| 
 | |
|   for (i = 0; i < numConsumers; i++)
 | |
|     cIterators[i] = c->end();
 | |
| }
 | |
| 
 | |
| template <typename container_t, typename element_t>
 | |
| DataListImpl<container_t, element_t>::DataListImpl(uint32_t nc) : DataList<element_t>()
 | |
| {
 | |
|   uint32_t i;
 | |
| 
 | |
|   numConsumers = nc;
 | |
|   itIndex = 0;
 | |
|   c = new container_t();
 | |
|   cIterators = new typename container_t::iterator[numConsumers];
 | |
| 
 | |
|   for (i = 0; i < numConsumers; i++)
 | |
|     cIterators[i] = c->end();
 | |
| }
 | |
| 
 | |
| template <typename container_t, typename element_t>
 | |
| DataListImpl<container_t, element_t>::DataListImpl(const DataListImpl<container_t, element_t>& dl)
 | |
|  : DataList<element_t>(dl)
 | |
| {
 | |
|   int i;
 | |
| 
 | |
|   c = dl.c;
 | |
|   numConsumers = dl.numConsumers;
 | |
|   itIndex = dl.itIndex;
 | |
| 
 | |
|   // delete [] cIterators;
 | |
|   cIterators = new typename container_t::iterator[numConsumers];
 | |
| 
 | |
|   for (i = 0; i < numConsumers; i++)
 | |
|     cIterators[i] = dl.cIterators[i];
 | |
| }
 | |
| 
 | |
| template <typename container_t, typename element_t>
 | |
| DataListImpl<container_t, element_t>::~DataListImpl()
 | |
| {
 | |
|   delete c;
 | |
|   delete[] cIterators;
 | |
| }
 | |
| 
 | |
| // lock at a higher level
 | |
| template <typename container_t, typename element_t>
 | |
| DataListImpl<container_t, element_t>& DataListImpl<container_t, element_t>::operator=(
 | |
|     const DataListImpl<container_t, element_t>& dl)
 | |
| {
 | |
|   if (&dl == this)
 | |
|   {
 | |
|     return *this;
 | |
|   }
 | |
|   uint64_t i;
 | |
| 
 | |
|   static_cast<DataList<element_t> >(*this) = static_cast<DataList<element_t> >(dl);
 | |
|   delete c;
 | |
|   c = dl.c;
 | |
|   numConsumers = dl.numConsumers;
 | |
|   itIndex = dl.itIndex;
 | |
| 
 | |
|   delete[] cIterators;
 | |
|   cIterators = new typename container_t::iterator[numConsumers];
 | |
| 
 | |
|   for (i = 0; i < numConsumers; i++)
 | |
|     cIterators[i] = dl.cIterators[i];
 | |
| 
 | |
|   return *this;
 | |
| }
 | |
| 
 | |
| template <typename container_t, typename element_t>
 | |
| uint64_t DataListImpl<container_t, element_t>::getIterator()
 | |
| {
 | |
|   if (itIndex >= numConsumers)
 | |
|   {
 | |
|     std::ostringstream oss;
 | |
|     oss << "DataListImpl::getIterator(): caller attempted to grab too many iterators: " << "have "
 | |
|         << numConsumers << " asked for " << (itIndex + 1);
 | |
|     throw std::logic_error(oss.str().c_str());
 | |
|   }
 | |
| 
 | |
|   cIterators[itIndex] = c->begin();
 | |
|   return itIndex++;
 | |
| }
 | |
| 
 | |
| template <typename container_t, typename element_t>
 | |
| inline void DataListImpl<container_t, element_t>::insert(const element_t& e)
 | |
| {
 | |
|   c->insert(c->end(), e);
 | |
| }
 | |
| 
 | |
| template <typename container_t, typename element_t>
 | |
| inline void DataListImpl<container_t, element_t>::insert(const std::vector<element_t>& v)
 | |
| {
 | |
|   if (typeid(container_t) == typeid(std::vector<element_t>))
 | |
|   {
 | |
|     auto* vc = (std::vector<element_t>*)c;
 | |
|     vc->insert(vc->end(), v.begin(), v.end());
 | |
|   }
 | |
|   else
 | |
|     throw std::logic_error("insert(vector) isn't supported for non-vector-based DLs yet");
 | |
| }
 | |
| 
 | |
| template <typename container_t, typename element_t>
 | |
| inline typename container_t::iterator DataListImpl<container_t, element_t>::iInsert(const element_t& e)
 | |
| {
 | |
|   return c->insert(c->end(), e);
 | |
| }
 | |
| 
 | |
| template <typename container_t, typename element_t>
 | |
| inline bool DataListImpl<container_t, element_t>::next(uint64_t id, element_t* e)
 | |
| {
 | |
|   // 	idbassert(id < numConsumers);
 | |
|   if (c == 0 || cIterators[id] == c->end())
 | |
|     return false;
 | |
| 
 | |
|   *e = *(cIterators[id]);
 | |
|   cIterators[id]++;
 | |
|   return true;
 | |
| }
 | |
| 
 | |
| template <typename container_t, typename element_t>
 | |
| bool DataListImpl<container_t, element_t>::endOfData(uint64_t id) const
 | |
| {
 | |
|   idbassert(id < numConsumers);
 | |
|   return (cIterators[id] == c->end());
 | |
| }
 | |
| 
 | |
| template <typename container_t, typename element_t>
 | |
| void DataListImpl<container_t, element_t>::eraseUpTo(uint64_t id)
 | |
| {
 | |
|   idbassert(id < numConsumers);
 | |
| #ifdef DEBUG
 | |
|   uint64_t i;
 | |
|   typename container_t::iterator it;
 | |
| 
 | |
|   for (it = c->begin(), i = 0; it != cIterators[id]; it++, i++)
 | |
|     ;
 | |
| 
 | |
|   std::cout << "DLI: erasing " << i << " elements" << std::endl;
 | |
| #endif
 | |
| 
 | |
|   c->erase(c->begin(), cIterators[id]);
 | |
| }
 | |
| 
 | |
| template <typename container_t, typename element_t>
 | |
| void DataListImpl<container_t, element_t>::reset()
 | |
| {
 | |
|   uint64_t i;
 | |
| 
 | |
|   delete c;
 | |
|   c = new container_t();
 | |
| 
 | |
|   for (i = 0; i < numConsumers; i++)
 | |
|     cIterators[i] = c->begin();
 | |
| }
 | |
| 
 | |
| template <typename container_t, typename element_t>
 | |
| void DataListImpl<container_t, element_t>::shrink()
 | |
| {
 | |
|   delete c;
 | |
|   c = 0;
 | |
| }
 | |
| 
 | |
| }  // namespace joblist
 |