zorba-coders team mailing list archive
-
zorba-coders team
-
Mailing list archive
-
Message #12127
[Merge] lp:~zorba-coders/zorba/markos-scratch into lp:zorba
Markos Zaharioudakis has proposed merging lp:~zorba-coders/zorba/markos-scratch into lp:zorba.
Requested reviews:
Markos Zaharioudakis (markos-za)
For more details, see:
https://code.launchpad.net/~zorba-coders/zorba/markos-scratch/+merge/114657
Streaming execution for tumbling windows (also fixes bug #1010051)
--
https://code.launchpad.net/~zorba-coders/zorba/markos-scratch/+merge/114657
Your team Zorba Coders is subscribed to branch lp:zorba.
=== modified file 'ChangeLog'
--- ChangeLog 2012-07-11 10:57:01 +0000
+++ ChangeLog 2012-07-12 14:52:27 +0000
@@ -26,6 +26,7 @@
* Big rewrite of plan serializer internals, resulting in big performance improvement.
* Avoid (if possible) treat expr for checking that the value of a non-external
global variable conforms to the type declaration of the vatiable.
+ * Streaming execution for tumbling windows (also fixes bug #1010051).
Bug Fixes/Other Changes:
* Fixed bug #1002993 (bug during revalidation after update; improper condition
=== modified file 'src/compiler/expression/flwor_expr.cpp'
--- src/compiler/expression/flwor_expr.cpp 2012-07-11 04:46:41 +0000
+++ src/compiler/expression/flwor_expr.cpp 2012-07-12 14:52:27 +0000
@@ -340,6 +340,9 @@
if (theWinStopCond != NULL)
theWinStopCond->set_flwor_clause(this);
+ if (winKind == tumbling_window)
+ theLazyEval = true;
+
if (varExpr != NULL && sctx != NULL)
{
RootTypeManager& rtm = GENV_TYPESYSTEM;
=== modified file 'src/runtime/core/gflwor/window_iterator.cpp'
--- src/runtime/core/gflwor/window_iterator.cpp 2012-07-11 05:28:20 +0000
+++ src/runtime/core/gflwor/window_iterator.cpp 2012-07-12 14:52:27 +0000
@@ -59,23 +59,23 @@
Constructor
********************************************************************************/
WindowVars::WindowVars (
- const std::vector<PlanIter_t >& aCurVars,
- const std::vector<PlanIter_t >& aPrevVars,
- const std::vector<PlanIter_t >& aNextVars,
- const std::vector<PlanIter_t >& aPosVars,
- const std::vector<PlanIter_t >& aCurOutVars,
- const std::vector<PlanIter_t >& aPrevOutVars,
- const std::vector<PlanIter_t >& aNextOutVars,
- const std::vector<PlanIter_t >& aPosOutVars)
+ const std::vector<PlanIter_t >& curVars,
+ const std::vector<PlanIter_t >& prevVars,
+ const std::vector<PlanIter_t >& nextVars,
+ const std::vector<PlanIter_t >& posVars,
+ const std::vector<PlanIter_t >& curOutVars,
+ const std::vector<PlanIter_t >& prevOutVars,
+ const std::vector<PlanIter_t >& nextOutVars,
+ const std::vector<PlanIter_t >& posOutVars)
:
- theCurVars(aCurVars),
- thePrevVars(aPrevVars),
- theNextVars(aNextVars),
- thePosVars(aPosVars),
- theCurOuterVars(aCurOutVars),
- thePrevOuterVars(aPrevOutVars),
- theNextOuterVars(aNextOutVars),
- thePosOuterVars(aPosOutVars)
+ theCurVars(curVars),
+ thePrevVars(prevVars),
+ theNextVars(nextVars),
+ thePosVars(posVars),
+ theCurOuterVars(curOutVars),
+ thePrevOuterVars(prevOutVars),
+ theNextOuterVars(nextOutVars),
+ thePosOuterVars(posOutVars)
{
}
@@ -136,57 +136,47 @@
/*******************************************************************************
Binds the variables inside the window clause.
- @param aPlanState The PlanState
+ @param planState The PlanState
@param aInputSeq The underlying input sequence
@param aPosition The position of the current item within the input sequence
(counting starts with 1).
********************************************************************************/
void WindowVars::bindIntern(
- PlanState& aPlanState,
- const store::TempSeq_t& aInputSeq,
- const ulong aPosition) const
+ PlanState& planState,
+ const store::TempSeq_t& inputSeq,
+ const ulong pos) const
{
- store::Item_t lItem;
+ store::Item_t item;
if (!theCurVars.empty())
{
- aInputSeq->getItem(xs_integer(aPosition), lItem);
- bindVariables(lItem, theCurVars, aPlanState);
+ inputSeq->getItem(xs_integer(pos), item);
+
+ bindVariables(item, theCurVars, planState);
}
if (!thePrevVars.empty())
{
- if (aPosition > 1)
- {
- aInputSeq->getItem(xs_integer(aPosition - 1), lItem);
- }
+ if (pos > 1)
+ inputSeq->getItem(xs_integer(pos - 1), item);
else
- {
- lItem = 0;
- }
+ item = NULL;
- bindVariables(lItem, thePrevVars, aPlanState);
+ bindVariables(item, thePrevVars, planState);
}
if (!theNextVars.empty())
{
- if (aInputSeq->containsItem(xs_integer(aPosition + 1)))
- {
- aInputSeq->getItem(xs_integer(aPosition + 1), lItem);
- }
- else
- {
- lItem = 0;
- }
+ inputSeq->getItem(xs_integer(pos + 1), item);
- bindVariables(lItem, theNextVars, aPlanState);
+ bindVariables(item, theNextVars, planState);
}
if (!thePosVars.empty())
{
- store::Item_t lPosItem;
- GENV_ITEMFACTORY->createInteger(lPosItem, xs_integer(aPosition));
- bindVariables(lPosItem, thePosVars, aPlanState);
+ GENV_ITEMFACTORY->createInteger(item, xs_integer(pos));
+
+ bindVariables(item, thePosVars, planState);
}
}
@@ -194,56 +184,47 @@
/*******************************************************************************
Binds the variables outside the window clause.
- @param aPlanState The PlanState
- @param aInputSeq The underlying input sequence
- @param aPosition The position of the current item within the input sequence
+ @param planState The PlanState
+ @param inputSeq The underlying input sequence
+ @param pos The position of the current item within the input sequence
(counting starts with 1).
********************************************************************************/
void WindowVars::bindExtern(
- PlanState& aPlanState,
- const store::TempSeq_t& aInputSeq,
- const ulong aPosition) const
+ PlanState& planState,
+ const store::TempSeq_t& inputSeq,
+ const ulong pos) const
{
- store::Item_t lItem;
+ store::Item_t item;
if (!theCurOuterVars.empty())
{
- aInputSeq->getItem(xs_integer(aPosition), lItem);
- bindVariables(lItem, theCurOuterVars, aPlanState);
+ inputSeq->getItem(xs_integer(pos), item);
+
+ bindVariables(item, theCurOuterVars, planState);
}
if (!thePrevOuterVars.empty())
{
- if (aPosition > 1)
- {
- aInputSeq->getItem(xs_integer(aPosition - 1), lItem);
- }
+ if (pos > 1)
+ inputSeq->getItem(xs_integer(pos - 1), item);
else
- {
- lItem = 0;
- }
+ item = NULL;
- bindVariables(lItem, thePrevOuterVars, aPlanState);
+ bindVariables(item, thePrevOuterVars, planState);
}
if (!theNextOuterVars.empty())
{
- if (aInputSeq->containsItem(xs_integer(aPosition + 1)))
- {
- aInputSeq->getItem(xs_integer(aPosition + 1), lItem);
- }
- else
- {
- lItem = 0;
- }
+ inputSeq->getItem(xs_integer(pos + 1), item);
- bindVariables(lItem, theNextOuterVars, aPlanState);
+ bindVariables(item, theNextOuterVars, planState);
}
if (!thePosOuterVars.empty())
{
- GENV_ITEMFACTORY->createInteger(lItem, Integer(aPosition));
- bindVariables(lItem, thePosOuterVars, aPlanState);
+ GENV_ITEMFACTORY->createInteger(item, Integer(pos));
+
+ bindVariables(item, thePosOuterVars, planState);
}
}
@@ -305,27 +286,27 @@
/***************************************************************************//**
********************************************************************************/
-void StartClause::open(PlanState& aPlanState, uint32_t& aOffset) const
-{
- theStartClauseIter->open(aPlanState, aOffset);
-}
-
-
-/***************************************************************************//**
-
-********************************************************************************/
-void StartClause::reset(PlanState& aPlanState) const
-{
- theStartClauseIter->reset(aPlanState);
-}
-
-
-/***************************************************************************//**
-
-********************************************************************************/
-void StartClause::close(PlanState& aPlanState) const
-{
- theStartClauseIter->close(aPlanState);
+void StartClause::open(PlanState& planState, uint32_t& aOffset) const
+{
+ theStartClauseIter->open(planState, aOffset);
+}
+
+
+/***************************************************************************//**
+
+********************************************************************************/
+void StartClause::reset(PlanState& planState) const
+{
+ theStartClauseIter->reset(planState);
+}
+
+
+/***************************************************************************//**
+
+********************************************************************************/
+void StartClause::close(PlanState& planState) const
+{
+ theStartClauseIter->close(planState);
}
@@ -335,13 +316,13 @@
expr.
********************************************************************************/
bool StartClause::evaluate(
- PlanState& aPlanState,
- const store::TempSeq_t& aInputSeq,
- const ulong aPosition) const
+ PlanState& planState,
+ const store::TempSeq_t& inputSeq,
+ const ulong pos) const
{
- theWindowVars.bindIntern(aPlanState, aInputSeq, aPosition);
+ theWindowVars.bindIntern(planState, inputSeq, pos);
- return evalToBool(theStartClauseIter, aPlanState);
+ return evalToBool(theStartClauseIter, planState);
}
@@ -351,11 +332,11 @@
the temp sequence that materializes the result of the domain expr.
********************************************************************************/
void StartClause::bindExtern(
- PlanState& aPlanState,
- const store::TempSeq_t& aInputSeq,
- const ulong aPosition) const
+ PlanState& planState,
+ const store::TempSeq_t& inputSeq,
+ const ulong pos) const
{
- theWindowVars.bindExtern(aPlanState, aInputSeq, aPosition);
+ theWindowVars.bindExtern(planState, inputSeq, pos);
}
@@ -363,11 +344,11 @@
********************************************************************************/
void StartClause::bindIntern(
- PlanState& aPlanState,
- const store::TempSeq_t& aInputSeq,
- const ulong aPosition) const
+ PlanState& planState,
+ const store::TempSeq_t& inputSeq,
+ const ulong pos) const
{
- theWindowVars.bindIntern(aPlanState, aInputSeq, aPosition);
+ theWindowVars.bindIntern(planState, inputSeq, pos);
}
@@ -456,30 +437,30 @@
/***************************************************************************//**
********************************************************************************/
-void EndClause::open(PlanState& aPlanState, uint32_t& aOffset) const
-{
- if (theHasEndClause)
- theEndClauseIter->open(aPlanState, aOffset);
-}
-
-
-/***************************************************************************//**
-
-********************************************************************************/
-void EndClause::reset(PlanState& aPlanState) const
-{
- if (theHasEndClause)
- theEndClauseIter->reset(aPlanState);
-}
-
-
-/***************************************************************************//**
-
-********************************************************************************/
-void EndClause::close(PlanState& aPlanState) const
-{
- if (theHasEndClause)
- theEndClauseIter->close(aPlanState);
+void EndClause::open(PlanState& planState, uint32_t& aOffset) const
+{
+ if (theHasEndClause)
+ theEndClauseIter->open(planState, aOffset);
+}
+
+
+/***************************************************************************//**
+
+********************************************************************************/
+void EndClause::reset(PlanState& planState) const
+{
+ if (theHasEndClause)
+ theEndClauseIter->reset(planState);
+}
+
+
+/***************************************************************************//**
+
+********************************************************************************/
+void EndClause::close(PlanState& planState) const
+{
+ if (theHasEndClause)
+ theEndClauseIter->close(planState);
}
@@ -487,13 +468,13 @@
********************************************************************************/
bool EndClause::evaluate(
- PlanState& aPlanState,
- const store::TempSeq_t& aInputSeq,
- const ulong aPosition) const
+ PlanState& planState,
+ const store::TempSeq_t& inputSeq,
+ const ulong pos) const
{
- theWindowVars.bindIntern(aPlanState, aInputSeq, aPosition);
+ theWindowVars.bindIntern(planState, inputSeq, pos);
- return evalToBool(theEndClauseIter, aPlanState);
+ return evalToBool(theEndClauseIter, planState);
}
@@ -501,11 +482,11 @@
********************************************************************************/
void EndClause::bindIntern(
- PlanState& aPlanState,
- const store::TempSeq_t& aInputSeq,
- const ulong aPosition) const
+ PlanState& planState,
+ const store::TempSeq_t& inputSeq,
+ const ulong pos) const
{
- theWindowVars.bindIntern(aPlanState, aInputSeq, aPosition);
+ theWindowVars.bindIntern(planState, inputSeq, pos);
}
@@ -513,11 +494,11 @@
********************************************************************************/
void EndClause::bindExtern(
- PlanState& aPlanState,
- const store::TempSeq_t& aInputSeq,
- const ulong aPosition) const
+ PlanState& planState,
+ const store::TempSeq_t& inputSeq,
+ const ulong pos) const
{
- theWindowVars.bindExtern(aPlanState, aInputSeq, aPosition);
+ theWindowVars.bindExtern(planState, inputSeq, pos);
}
@@ -561,9 +542,9 @@
}
-void WindowState::reset(PlanState& aPlanState)
+void WindowState::reset(PlanState& planState)
{
- PlanIteratorState::reset(aPlanState);
+ PlanIteratorState::reset(planState);
theCurInputPos = 1;
theDomainSeq = NULL;
theOpenWindows.clear();
@@ -607,6 +588,9 @@
theMaxNeededHistory(maxNeededHistory)
{
castIterVector<LetVarIterator>(theVarRefs, varRefs);
+
+ if (theWindowType == TUMBLING)
+ theMaxNeededHistory = 1;
}
@@ -685,44 +669,44 @@
/***************************************************************************//**
********************************************************************************/
-void WindowIterator::openImpl(PlanState& aPlanState, uint32_t& aOffset)
+void WindowIterator::openImpl(PlanState& planState, uint32_t& aOffset)
{
- StateTraitsImpl<WindowState>::createState(aPlanState, theStateOffset, aOffset);
-
- theTupleIter->open(aPlanState, aOffset);
- theInputIter->open(aPlanState, aOffset);
-
- theStartClause.open(aPlanState, aOffset);
- theEndClause.open(aPlanState, aOffset);
+ StateTraitsImpl<WindowState>::createState(planState, theStateOffset, aOffset);
+
+ theTupleIter->open(planState, aOffset);
+ theInputIter->open(planState, aOffset);
+
+ theStartClause.open(planState, aOffset);
+ theEndClause.open(planState, aOffset);
}
/***************************************************************************//**
********************************************************************************/
-void WindowIterator::resetImpl(PlanState& aPlanState) const
+void WindowIterator::resetImpl(PlanState& planState) const
{
- WindowState* lState = StateTraitsImpl<WindowState>::getState(aPlanState,
+ WindowState* lState = StateTraitsImpl<WindowState>::getState(planState,
theStateOffset);
- lState->reset(aPlanState);
+ lState->reset(planState);
- theTupleIter->reset(aPlanState);
- theInputIter->reset(aPlanState);
- theStartClause.reset(aPlanState);
- theEndClause.reset(aPlanState);
+ theTupleIter->reset(planState);
+ theInputIter->reset(planState);
+ theStartClause.reset(planState);
+ theEndClause.reset(planState);
}
/***************************************************************************//**
********************************************************************************/
-void WindowIterator::closeImpl(PlanState& aPlanState)
+void WindowIterator::closeImpl(PlanState& planState)
{
- theTupleIter->close(aPlanState);
- theInputIter->close(aPlanState);
- theStartClause.close(aPlanState);
- theEndClause.close(aPlanState);
- StateTraitsImpl<WindowState>::destroyState(aPlanState, theStateOffset);
+ theTupleIter->close(planState);
+ theInputIter->close(planState);
+ theStartClause.close(planState);
+ theEndClause.close(planState);
+ StateTraitsImpl<WindowState>::destroyState(planState, theStateOffset);
}
@@ -731,8 +715,8 @@
of the domain sequence.
********************************************************************************/
void WindowIterator::bindVariable(
- PlanState& aPlanState,
- store::TempSeq_t& aInputSeq,
+ PlanState& planState,
+ store::TempSeq_t& inputSeq,
ulong aStartPos,
ulong aEndPos) const
{
@@ -743,7 +727,7 @@
lVarIter != theVarRefs.end();
++lVarIter)
{
- (*lVarIter)->bind(aInputSeq, aPlanState, lStartPos, lEndPos);
+ (*lVarIter)->bind(inputSeq, planState, lStartPos, lEndPos);
}
}
@@ -759,11 +743,14 @@
if (lState->theOpenWindows.empty())
{
if (lState->theCurInputPos > theMaxNeededHistory)
- lState->theDomainSeq->purgeUpTo(xs_integer(lState->theCurInputPos - theMaxNeededHistory));
+ lState->theDomainSeq->
+ purgeUpTo(xs_integer(lState->theCurInputPos - theMaxNeededHistory));
}
else
{
- int32_t lPurgeTo = lState->theOpenWindows.front().theStartPos - theMaxNeededHistory;
+ int64_t lPurgeTo =
+ lState->theOpenWindows.front().theStartPos - theMaxNeededHistory;
+
if (lPurgeTo > 0)
lState->theDomainSeq->purgeUpTo(xs_integer(lPurgeTo));
}
@@ -774,71 +761,72 @@
/***************************************************************************//**
********************************************************************************/
-bool WindowIterator::nextImpl(store::Item_t& aResult, PlanState& aPlanState) const
+bool WindowIterator::nextImpl(store::Item_t& aResult, PlanState& planState) const
{
store::Iterator_t iterator;
- WindowState* lState;
- DEFAULT_STACK_INIT(WindowState, lState, aPlanState);
+
+ WindowState* state;
+ DEFAULT_STACK_INIT(WindowState, state, planState);
// Pull the next tuple from the input stream
- while (consumeNext(aResult, theTupleIter, aPlanState))
+ while (consumeNext(aResult, theTupleIter, planState))
{
// Create the temp sequence where to materialize the result of the domain
// expr (lazily if theLazyEval flag is true).
- iterator = new PlanIteratorWrapper(theInputIter, aPlanState);
- lState->theDomainSeq = GENV_STORE.createTempSeq(iterator, theLazyEval);
+ iterator = new PlanIteratorWrapper(theInputIter, planState);
+ state->theDomainSeq = GENV_STORE.createTempSeq(iterator, theLazyEval);
// Its clever to switch quite early to avoid a lot of if-else statements
if (theWindowType == WindowIterator::SLIDING)
{
// Get the next item from the domain sequence
// TODO: can the xs_integer be hoisted?
- while (lState->theDomainSeq->containsItem(xs_integer(lState->theCurInputPos)))
+ while (state->theDomainSeq->containsItem(xs_integer(state->theCurInputPos)))
{
// If the current item satisfies the start condition, create a candidate
// window starting at the current domain item.
- if (theStartClause.evaluate(aPlanState,
- lState->theDomainSeq,
- lState->theCurInputPos))
+ if (theStartClause.evaluate(planState,
+ state->theDomainSeq,
+ state->theCurInputPos))
{
- lState->theOpenWindows.push_back(WindowDef(lState->theCurInputPos));
+ state->theOpenWindows.push_back(WindowDef(state->theCurInputPos));
}
// For each candidate window, check if the current domain item satisfies
// the end condition. Notice that before evaluating the end condition
// expr, we must rebind the internal vars of the start condition, because
// those varaibles may be refrenced in the end cond expr.
- lState->theCurWindow = lState->theOpenWindows.begin();
+ state->theCurWindow = state->theOpenWindows.begin();
- while ( lState->theCurWindow != lState->theOpenWindows.end() )
+ while ( state->theCurWindow != state->theOpenWindows.end() )
{
- if (lState->theCurWindow->theEndPos == 0)
+ if (state->theCurWindow->theEndPos == 0)
{
- theStartClause.bindIntern(aPlanState,
- lState->theDomainSeq,
- lState->theCurWindow->theStartPos);
+ theStartClause.bindIntern(planState,
+ state->theDomainSeq,
+ state->theCurWindow->theStartPos);
- ulong lCurPos = lState->theCurInputPos;
- if ( theEndClause.evaluate(aPlanState,
- lState->theDomainSeq,
+ ulong lCurPos = state->theCurInputPos;
+ if ( theEndClause.evaluate(planState,
+ state->theDomainSeq,
lCurPos))
{
- lState->theCurWindow->theEndPos = lCurPos;
+ state->theCurWindow->theEndPos = lCurPos;
}
}
- ++lState->theCurWindow;
+ ++state->theCurWindow;
}
// Try to return closed windows to the consumer iterator. Notice that
// windows must be sorted according to the position of their starting
// items in the domain sequence. So, we can return a closed window only
- // if it appears as the first window in lState->theOpenWindows.
- lState->theCurWindow = lState->theOpenWindows.begin();
+ // if it appears as the first window in state->theOpenWindows.
+ state->theCurWindow = state->theOpenWindows.begin();
- while (!lState->theOpenWindows.empty())
+ while (!state->theOpenWindows.empty())
{
- if (lState->theCurWindow->theEndPos != 0)
+ if (state->theCurWindow->theEndPos != 0)
{
// The current window is closed and its starting item is before the
// stating items of all other windows (open or closed) in the domain
@@ -849,23 +837,24 @@
// evaluations of the start and/or end conditions, and (d) return to
// the caller a new tuple that consists of the current input tuple
// augmented with one column per variable that was bound in this step.
- theStartClause.bindExtern(aPlanState,
- lState->theDomainSeq,
- lState->theCurWindow->theStartPos);
-
- theEndClause.bindExtern(aPlanState,
- lState->theDomainSeq,
- lState->theCurWindow->theEndPos);
-
- bindVariable(aPlanState,
- lState->theDomainSeq,
- lState->theCurWindow->theStartPos,
- lState->theCurWindow->theEndPos);
-
- lState->theCurWindow = lState->theOpenWindows.erase(lState->theCurWindow);
- doGarbageCollection(lState);
-
- STACK_PUSH(true, lState);
+ theStartClause.bindExtern(planState,
+ state->theDomainSeq,
+ state->theCurWindow->theStartPos);
+
+ theEndClause.bindExtern(planState,
+ state->theDomainSeq,
+ state->theCurWindow->theEndPos);
+
+ bindVariable(planState,
+ state->theDomainSeq,
+ state->theCurWindow->theStartPos,
+ state->theCurWindow->theEndPos);
+
+ state->theCurWindow = state->theOpenWindows.erase(state->theCurWindow);
+
+ //doGarbageCollection(state);
+
+ STACK_PUSH(true, state);
}
else
{
@@ -873,7 +862,7 @@
}
}
- ++lState->theCurInputPos;
+ ++state->theCurInputPos;
}
}
else //Tumpling window
@@ -881,123 +870,126 @@
// Doing this switch now also avoids further overhad
if (theEndClause.theHasEndClause)
{
- // TODO: can the xs_integer be hoisted?
- while (lState->theDomainSeq->containsItem(xs_integer(lState->theCurInputPos)))
+ while (state->theDomainSeq->containsItem(xs_integer(state->theCurInputPos)))
{
- if (lState->theOpenWindows.empty() &&
- theStartClause.evaluate(aPlanState,
- lState->theDomainSeq,
- lState->theCurInputPos))
- {
- theStartClause.bindExtern(aPlanState,
- lState->theDomainSeq,
- lState->theCurInputPos);
-
- lState->theOpenWindows.push_back(lState->theCurInputPos);
- }
-
- if ( !lState->theOpenWindows.empty() &&
- theEndClause.evaluate(aPlanState,
- lState->theDomainSeq,
- lState->theCurInputPos))
- {
- theEndClause.bindExtern(aPlanState,
- lState->theDomainSeq,
- lState->theCurInputPos);
-
- bindVariable(aPlanState,
- lState->theDomainSeq,
- lState->theOpenWindows[0].theStartPos,
- lState->theCurInputPos);
-
- lState->theOpenWindows.pop_back();
-
- assert(lState->theOpenWindows.empty());
-
- doGarbageCollection(lState);
-
- STACK_PUSH(true, lState);
- }
- ++lState->theCurInputPos;
+ if (state->theOpenWindows.empty() &&
+ theStartClause.evaluate(planState,
+ state->theDomainSeq,
+ state->theCurInputPos))
+ {
+ theStartClause.bindExtern(planState,
+ state->theDomainSeq,
+ state->theCurInputPos);
+
+ state->theOpenWindows.push_back(state->theCurInputPos);
+ }
+
+ if ( !state->theOpenWindows.empty() &&
+ theEndClause.evaluate(planState,
+ state->theDomainSeq,
+ state->theCurInputPos))
+ {
+ theEndClause.bindExtern(planState,
+ state->theDomainSeq,
+ state->theCurInputPos);
+
+ bindVariable(planState,
+ state->theDomainSeq,
+ state->theOpenWindows[0].theStartPos,
+ state->theCurInputPos);
+
+ state->theOpenWindows.pop_back();
+
+ assert(state->theOpenWindows.empty());
+
+ STACK_PUSH(true, state);
+
+ doGarbageCollection(state);
+ }
+
+ ++state->theCurInputPos;
}
}
else
{
- // TODO: can the xs_integer be hoisted?
- while (lState->theDomainSeq->containsItem(xs_integer(lState->theCurInputPos)))
+ while (state->theDomainSeq->containsItem(xs_integer(state->theCurInputPos)))
{
- if (theStartClause.evaluate(aPlanState,
- lState->theDomainSeq,
- lState->theCurInputPos))
+ if (theStartClause.evaluate(planState,
+ state->theDomainSeq,
+ state->theCurInputPos))
{
- if (!lState->theOpenWindows.empty())
+ if (!state->theOpenWindows.empty())
{
//In no case there should be more than 1 position inside
- assert(lState->theOpenWindows.size() == 1);
-
- theStartClause.bindExtern(aPlanState,
- lState->theDomainSeq,
- lState->theOpenWindows[0].theStartPos);
-
- bindVariable(aPlanState,
- lState->theDomainSeq,
- lState->theOpenWindows[0].theStartPos,
- lState->theCurInputPos -1);
-
- lState->theOpenWindows.pop_back();
-
- doGarbageCollection(lState);
-
- STACK_PUSH(true, lState);
+ assert(state->theOpenWindows.size() == 1);
+
+ theStartClause.bindExtern(planState,
+ state->theDomainSeq,
+ state->theOpenWindows[0].theStartPos);
+
+ bindVariable(planState,
+ state->theDomainSeq,
+ state->theOpenWindows[0].theStartPos,
+ state->theCurInputPos - 1);
+
+ state->theOpenWindows.pop_back();
+
+ assert(state->theOpenWindows.empty());
+
+ STACK_PUSH(true, state);
+
+ --state->theCurInputPos;
+ doGarbageCollection(state);
+ ++state->theCurInputPos;
}
- lState->theOpenWindows.push_back(lState->theCurInputPos);
+ state->theOpenWindows.push_back(state->theCurInputPos);
}
- ++lState->theCurInputPos;
+ ++state->theCurInputPos;
}
}
}
// Check if we have open and/or closed windows
- lState->theCurWindow = lState->theOpenWindows.begin();
+ state->theCurWindow = state->theOpenWindows.begin();
- while (lState->theCurWindow != lState->theOpenWindows.end())
+ while (state->theCurWindow != state->theOpenWindows.end())
{
- if (!theEndClause.theOnlyEnd || lState->theCurWindow->theEndPos != 0)
+ if (!theEndClause.theOnlyEnd || state->theCurWindow->theEndPos != 0)
{
- if (lState->theCurWindow->theEndPos == 0)
- lState->theCurWindow->theEndPos = lState->theCurInputPos - 1;
-
- bindVariable(aPlanState,
- lState->theDomainSeq,
- lState->theOpenWindows[0].theStartPos,
- lState->theCurWindow->theEndPos);
-
- theStartClause.bindExtern(aPlanState,
- lState->theDomainSeq,
- lState->theOpenWindows[0].theStartPos);
-
- theEndClause.bindExtern(aPlanState,
- lState->theDomainSeq,
- lState->theCurWindow->theEndPos);
-
- lState->theCurWindow = lState->theOpenWindows.erase(lState->theCurWindow);
-
- STACK_PUSH(true, lState);
+ if (state->theCurWindow->theEndPos == 0)
+ state->theCurWindow->theEndPos = state->theCurInputPos - 1;
+
+ bindVariable(planState,
+ state->theDomainSeq,
+ state->theOpenWindows[0].theStartPos,
+ state->theCurWindow->theEndPos);
+
+ theStartClause.bindExtern(planState,
+ state->theDomainSeq,
+ state->theOpenWindows[0].theStartPos);
+
+ theEndClause.bindExtern(planState,
+ state->theDomainSeq,
+ state->theCurWindow->theEndPos);
+
+ state->theCurWindow = state->theOpenWindows.erase(state->theCurWindow);
+
+ STACK_PUSH(true, state);
}
else
{
- ++lState->theCurWindow;
+ ++state->theCurWindow;
}
}
- theInputIter->reset(aPlanState);
- lState->reset(aPlanState);
+ theInputIter->reset(planState);
+ state->reset(planState);
}
- STACK_PUSH(false, lState);
- STACK_END(lState);
+ STACK_PUSH(false, state);
+ STACK_END(state);
}
} //Namespace flwor
=== modified file 'src/runtime/core/trycatch.cpp'
--- src/runtime/core/trycatch.cpp 2012-07-11 04:46:41 +0000
+++ src/runtime/core/trycatch.cpp 2012-07-12 14:52:27 +0000
@@ -77,17 +77,22 @@
TryCatchIteratorState::reset(PlanState& planState)
{
PlanIteratorState::reset(planState);
+
if ( theTargetSequence )
theTargetSequence->purge(); // release the target sequence
- if (theTempIterator != NULL) {
+
+ if (theTempIterator != NULL)
+ {
theTempIterator->close();
theTempIterator = NULL;
}
+
theCatchIterator = NULL;
std::vector<store::Iterator_t>::iterator lIters = theErrorIters.begin();
std::vector<store::Iterator_t>::iterator lItersEnd = theErrorIters.end();
- for (; lIters != lItersEnd; ++lIters) {
+ for (; lIters != lItersEnd; ++lIters)
+ {
(*lIters)->close();
}
@@ -521,6 +526,7 @@
}
}
+
bool
TryCatchIterator::nextImpl(store::Item_t& result, PlanState& planState) const
{
@@ -579,15 +585,20 @@
theChild->reset(planState);
- std::vector<TryCatchIterator::CatchClause>::const_iterator lIter = theCatchClauses.begin();
- std::vector<TryCatchIterator::CatchClause>::const_iterator lEnd = theCatchClauses.end();
-
- for ( ; lIter != lEnd; ++lIter ) {
+ std::vector<TryCatchIterator::CatchClause>::const_iterator lIter =
+ theCatchClauses.begin();
+
+ std::vector<TryCatchIterator::CatchClause>::const_iterator lEnd =
+ theCatchClauses.end();
+
+ for ( ; lIter != lEnd; ++lIter )
+ {
( *lIter ).catch_expr->reset(planState);
}
}
+
void
TryCatchIterator::closeImpl(PlanState& planState)
{
@@ -603,7 +614,9 @@
StateTraitsImpl<TryCatchIteratorState>::destroyState(planState, theStateOffset);
}
-void TryCatchIterator::accept(PlanIterVisitor &v) const {
+
+void TryCatchIterator::accept(PlanIterVisitor &v) const
+{
v.beginVisit(*this);
theChild->accept ( v );
std::vector<TryCatchIterator::CatchClause>::const_iterator lIter = theCatchClauses.begin();
=== modified file 'src/runtime/core/trycatch.h'
--- src/runtime/core/trycatch.h 2012-07-11 04:46:41 +0000
+++ src/runtime/core/trycatch.h 2012-07-12 14:52:27 +0000
@@ -36,9 +36,11 @@
void reset(PlanState&);
// used for evaluating the target expression eagerly
- store::TempSeq_t theTargetSequence;
- store::Iterator_t theTempIterator;
- PlanIter_t theCatchIterator;
+ store::TempSeq_t theTargetSequence;
+
+ store::Iterator_t theTempIterator;
+
+ PlanIter_t theCatchIterator;
std::vector<store::Iterator_t> theErrorIters;
};
@@ -119,8 +121,9 @@
void resetImpl(PlanState& planState) const;
void closeImpl(PlanState& planState);
- virtual void accept(PlanIterVisitor& v) const;
- virtual uint32_t getStateSizeOfSubtree() const;
+ void accept(PlanIterVisitor& v) const;
+
+ uint32_t getStateSizeOfSubtree() const;
protected:
bool matchedCatch(
=== modified file 'src/runtime/core/var_iterators.cpp'
--- src/runtime/core/var_iterators.cpp 2012-07-11 04:46:41 +0000
+++ src/runtime/core/var_iterators.cpp 2012-07-12 14:52:27 +0000
@@ -578,7 +578,8 @@
else if (state->theTempSeq != NULL)
{
if (state->theSourceIter == NULL)
- state->theSourceIter = GENV_STORE.getIteratorFactory()->createTempSeqIterator();
+ state->theSourceIter = GENV_STORE.getIteratorFactory()->
+ createTempSeqIterator(false);
state->theSourceIter->init(state->theTempSeq);
state->theSourceIter->open();
@@ -800,7 +801,8 @@
else
{
if (state->theTempSeqIter == NULL)
- state->theTempSeqIter = GENV_STORE.getIteratorFactory()->createTempSeqIterator();
+ state->theTempSeqIter = GENV_STORE.getIteratorFactory()->
+ createTempSeqIterator(false);
state->theTempSeqIter->init(value);
state->theTempSeqIter->open();
@@ -832,7 +834,8 @@
else
{
if (state->theTempSeqIter == NULL)
- state->theTempSeqIter = GENV_STORE.getIteratorFactory()->createTempSeqIterator();
+ state->theTempSeqIter = GENV_STORE.getIteratorFactory()->
+ createTempSeqIterator(value->isLazy());
state->theTempSeqIter->init(value, startPos, endPos);
state->theTempSeqIter->open();
=== modified file 'src/store/api/iterator.h'
--- src/store/api/iterator.h 2012-07-11 04:46:41 +0000
+++ src/store/api/iterator.h 2012-07-12 14:52:27 +0000
@@ -207,8 +207,6 @@
virtual void open() = 0;
- virtual Item* next() = 0;
-
virtual bool next(Item_t& result) = 0;
virtual void reset() = 0;
=== modified file 'src/store/api/iterator_factory.h'
--- src/store/api/iterator_factory.h 2012-07-11 04:46:41 +0000
+++ src/store/api/iterator_factory.h 2012-07-12 14:52:27 +0000
@@ -62,7 +62,7 @@
* Create an iterator to iterate over the items of a temp sequence.
*/
virtual TempSeqIterator*
- createTempSeqIterator() = 0;
+ createTempSeqIterator(bool lazy) = 0;
};
=== modified file 'src/store/api/temp_seq.h'
--- src/store/api/temp_seq.h 2012-07-11 04:46:41 +0000
+++ src/store/api/temp_seq.h 2012-07-12 14:52:27 +0000
@@ -36,6 +36,18 @@
public:
virtual ~TempSeq(){}
+ virtual bool isLazy() const = 0;
+
+ /**
+ * @return Does this TempSeq save an empty sequence?
+ */
+ virtual bool empty() = 0;
+
+ /**
+ *
+ */
+ virtual xs_integer getSize() const = 0;
+
/**
* Initializes a temp sequence with the given input iterator
*/
@@ -63,12 +75,7 @@
*
* @param upTo boundary for garbage collector
*/
- virtual void purgeUpTo(xs_integer upTo) = 0;
-
- /**
- * @return Does this TempSeq save an empty sequence?
- */
- virtual bool empty() = 0;
+ virtual void purgeUpTo(xs_integer pos) = 0;
/**
* Gets an item at a certain position.
@@ -78,7 +85,7 @@
* @param position (first position in XQuery is 1 and not 0!)
* @return item
*/
- virtual void getItem(xs_integer position, Item_t& result) = 0;
+ virtual void getItem(xs_integer pos, Item_t& result) = 0;
/**
* Returns true if the item at the passed position is available.
@@ -88,12 +95,7 @@
* @param position
* @return
*/
- virtual bool containsItem(xs_integer position) = 0;
-
- /**
- *
- */
- virtual xs_integer getSize() const = 0;
+ virtual bool containsItem(xs_integer pos) = 0;
/**
* Reads the whole Sequence from beginning to end; it is allowed to have several
@@ -104,18 +106,6 @@
*/
virtual Iterator_t getIterator() const = 0;
- /**
- * Returns an iterator which reads just a part of the underlying TempSeq
- * Starts counting with 1.
- *
- * @param startPos The first item which the iterator returns. Starts counting with 1.
- * @param endPos The last item which the iterator returns
- * @return Iterator
- */
- virtual Iterator_t getIterator(
- xs_integer startPos,
- xs_integer endPos,
- bool streaming = false) const = 0;
};
} // namespace store
=== modified file 'src/store/naive/simple_iterator_factory.cpp'
--- src/store/naive/simple_iterator_factory.cpp 2012-07-11 04:46:41 +0000
+++ src/store/naive/simple_iterator_factory.cpp 2012-07-12 14:52:27 +0000
@@ -19,6 +19,7 @@
#include "simple_iterator_factory.h"
#include "node_iterators.h"
#include "simple_temp_seq.h"
+#include "simple_lazy_temp_seq.h"
#include "simple_index.h"
#include "simple_index_value.h"
#include "simple_index_general.h"
@@ -83,9 +84,12 @@
/*******************************************************************************
********************************************************************************/
-store::TempSeqIterator* SimpleIteratorFactory::createTempSeqIterator()
+store::TempSeqIterator* SimpleIteratorFactory::createTempSeqIterator(bool lazy)
{
- return new SimpleTempSeqIter();
+ if (lazy)
+ return new SimpleLazyTempSeqIter();
+ else
+ return new SimpleTempSeqIter();
}
=== modified file 'src/store/naive/simple_iterator_factory.h'
--- src/store/naive/simple_iterator_factory.h 2012-07-11 04:46:41 +0000
+++ src/store/naive/simple_iterator_factory.h 2012-07-12 14:52:27 +0000
@@ -39,7 +39,7 @@
store::IndexProbeIterator* createIndexProbeIterator(const store::Index_t& index);
- store::TempSeqIterator* createTempSeqIterator();
+ store::TempSeqIterator* createTempSeqIterator(bool lazy);
};
}
=== modified file 'src/store/naive/simple_lazy_temp_seq.cpp'
--- src/store/naive/simple_lazy_temp_seq.cpp 2012-07-11 04:46:41 +0000
+++ src/store/naive/simple_lazy_temp_seq.cpp 2012-07-12 14:52:27 +0000
@@ -33,9 +33,9 @@
/*******************************************************************************
********************************************************************************/
-SimpleLazyTempSeq::SimpleLazyTempSeq(const store::Iterator_t& aIter)
+SimpleLazyTempSeq::SimpleLazyTempSeq(const store::Iterator_t& iter)
{
- init(aIter);
+ init(iter);
}
@@ -44,66 +44,42 @@
********************************************************************************/
SimpleLazyTempSeq::~SimpleLazyTempSeq()
{
+ clear();
}
/*******************************************************************************
********************************************************************************/
-void SimpleLazyTempSeq::init(const store::Iterator_t& aIter)
+void SimpleLazyTempSeq::clear()
{
- theIterator = aIter;
- theMatFinished = false;
- thePurgedUpTo = 0;
+ std::vector<store::Item*>::iterator ite = theItems.begin();
+ std::vector<store::Item*>::iterator end = theItems.end();
+ for (; ite != end; ++ite)
+ {
+ (*ite)->removeReference();
+ }
+
theItems.clear();
}
/*******************************************************************************
-
-********************************************************************************/
-void SimpleLazyTempSeq::append(const store::Iterator_t& iter)
-{
- while (!theMatFinished)
- {
- matNextItem();
- }
-
- theMatFinished = false;
- theIterator = iter;
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-void SimpleLazyTempSeq::purge()
-{
- //Not supported
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-void SimpleLazyTempSeq::purgeUpTo(xs_integer upTo)
-{
- xs_long lUpTo;
- try
- {
- lUpTo = to_xs_long(upTo);
- }
- catch (std::range_error& e)
- {
- throw ZORBA_EXCEPTION(zerr::ZSTR0060_RANGE_EXCEPTION,
- ERROR_PARAMS(BUILD_STRING("sequence too big (" << e.what() << ")")));
- }
-
- ZORBA_ASSERT(lUpTo >= thePurgedUpTo);
- ZORBA_ASSERT(lUpTo - thePurgedUpTo <= theItems.size());
-
- theItems.erase(theItems.begin(), (theItems.begin() + (lUpTo - thePurgedUpTo)));
- thePurgedUpTo = lUpTo;
+ Get the next item (if any) from the input iterator and put it at the end of
+ the queue.
+********************************************************************************/
+void SimpleLazyTempSeq::matNextItem()
+{
+ store::Item_t item;
+
+ if (! theIterator->next(item))
+ {
+ theMatFinished = true;
+ }
+ else
+ {
+ theItems.push_back(item.release());
+ }
}
@@ -134,12 +110,97 @@
/*******************************************************************************
********************************************************************************/
+xs_integer SimpleLazyTempSeq::getSize() const
+{
+ ZORBA_ASSERT(false);
+ return xs_integer(thePurgedUpTo + theItems.size());
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+void SimpleLazyTempSeq::init(const store::Iterator_t& iter)
+{
+ theIterator = iter;
+
+ theMatFinished = false;
+ thePurgedUpTo = 0;
+
+ clear();
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+void SimpleLazyTempSeq::append(const store::Iterator_t& iter)
+{
+ while (!theMatFinished)
+ {
+ matNextItem();
+ }
+
+ theMatFinished = false;
+ theIterator = iter;
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+void SimpleLazyTempSeq::purge()
+{
+ theIterator = NULL;
+
+ theMatFinished = false;
+ thePurgedUpTo = 0;
+
+ clear();
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+void SimpleLazyTempSeq::purgeUpTo(xs_integer position)
+{
+ xs_long pos;
+ try
+ {
+ pos = to_xs_long(position);
+ }
+ catch (std::range_error& e)
+ {
+ throw ZORBA_EXCEPTION(zerr::ZSTR0060_RANGE_EXCEPTION,
+ ERROR_PARAMS(BUILD_STRING("sequence too big (" << e.what() << ")")));
+ }
+
+ ZORBA_ASSERT(pos >= thePurgedUpTo);
+ ZORBA_ASSERT(pos - thePurgedUpTo <= theItems.size());
+
+ std::vector<store::Item*>::iterator ite = theItems.begin();
+ std::vector<store::Item*>::iterator end = theItems.begin() + (pos - thePurgedUpTo);
+ for (; ite != end; ++ite)
+ {
+ (*ite)->removeReference();
+ }
+
+ theItems.erase(theItems.begin(), end);
+
+ thePurgedUpTo = pos;
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
void SimpleLazyTempSeq::getItem(xs_integer position, store::Item_t& result)
{
- xs_long lPos;
+ xs_long pos;
try
{
- lPos = to_xs_long(position);
+ pos = to_xs_long(position);
}
catch (std::range_error& e)
{
@@ -147,9 +208,18 @@
ERROR_PARAMS(BUILD_STRING("access out of bounds " << e.what() << ")")));
}
- if (this->containsItem(position))
- {
- result = theItems[lPos - thePurgedUpTo - 1];
+ ZORBA_ASSERT(pos > thePurgedUpTo);
+
+ xs_long numItemsToBuffer = pos - thePurgedUpTo;
+
+ while (!theMatFinished && theItems.size() < numItemsToBuffer)
+ {
+ matNextItem();
+ }
+
+ if (theItems.size() >= numItemsToBuffer)
+ {
+ result = theItems[pos - thePurgedUpTo - 1];
}
else
{
@@ -180,10 +250,10 @@
********************************************************************************/
inline bool SimpleLazyTempSeq::containsItem(xs_integer position)
{
- xs_long lPos;
+ xs_long pos;
try
{
- lPos = to_xs_long(position);
+ pos = to_xs_long(position);
}
catch (std::range_error& e)
{
@@ -191,9 +261,9 @@
ERROR_PARAMS(BUILD_STRING("access out of bounds " << e.what() << ")")));
}
- assert(lPos > thePurgedUpTo);
+ ZORBA_ASSERT(pos > thePurgedUpTo);
- xs_long numItemsToBuffer = lPos - thePurgedUpTo;
+ xs_long numItemsToBuffer = pos - thePurgedUpTo;
while (!theMatFinished && theItems.size() < numItemsToBuffer)
{
@@ -205,44 +275,6 @@
/*******************************************************************************
- Get the next item (if any) from the input iterator and put it at the end of
- the queue.
-********************************************************************************/
-void SimpleLazyTempSeq::matNextItem()
-{
- theItems.push_back(NULL);
-
- store::Item_t& lLocation = theItems.back();
-
- if (theIterator->next(lLocation))
- {
- if (theCopy && lLocation->isNode())
- {
- store::CopyMode lCopyMode;
- lLocation = lLocation->copy(NULL, lCopyMode);
- }
- }
- else
- {
- // We do not want to have an empty item materialized.
- theItems.pop_back();
- theMatFinished = true;
- theIterator->close();
- }
-}
-
-
-/*******************************************************************************
-
-********************************************************************************/
-xs_integer SimpleLazyTempSeq::getSize() const
-{
- ZORBA_ASSERT(false);
- return xs_integer(0);
-}
-
-
-/*******************************************************************************
Reads the whole Sequence from beginning to end; it is allowed to have several
concurrent iterators on the same TempSeq.
@@ -250,23 +282,28 @@
********************************************************************************/
store::Iterator_t SimpleLazyTempSeq::getIterator() const
{
- return new SimpleLazyTempSeqIter(this, xs_integer(1), xs_integer(std::numeric_limits<long>::max()));
+ return new SimpleLazyTempSeqIter(this,
+ xs_integer(1),
+ xs_integer(std::numeric_limits<long>::max()));
}
+/////////////////////////////////////////////////////////////////////////////////
+// //
+// SimpleLazyTempSeqIter //
+// //
+/////////////////////////////////////////////////////////////////////////////////
+
+
/*******************************************************************************
- Returns an iterator which reads just a part of the underlying TempSeq
- @param startPos The first item which the iterator returns
- @param endPos The last item which the iterator returns
- @return Iterator
********************************************************************************/
-store::Iterator_t SimpleLazyTempSeq::getIterator(
- xs_integer startPos,
- xs_integer endPos,
- bool streaming) const
+SimpleLazyTempSeqIter::SimpleLazyTempSeqIter()
+ :
+ theCurPos(0),
+ theStartPos(0),
+ theEndPos(0)
{
- return new SimpleLazyTempSeqIter(this, startPos, endPos);
}
@@ -274,17 +311,17 @@
********************************************************************************/
SimpleLazyTempSeqIter::SimpleLazyTempSeqIter(
- const SimpleLazyTempSeq* aTempSeq,
- xs_integer aStartPos,
- xs_integer aEndPos)
+ const SimpleLazyTempSeq* tempSeq,
+ xs_integer startPos,
+ xs_integer endPos)
:
- theTempSeq(const_cast<SimpleLazyTempSeq*>(aTempSeq))
+ theTempSeq(const_cast<SimpleLazyTempSeq*>(tempSeq))
{
try
{
- theCurPos = to_xs_long(aStartPos) - 1;
- theStartPos = to_xs_long(aStartPos);
- theEndPos = to_xs_long(aEndPos);
+ theStartPos = to_xs_long(startPos);
+ theEndPos = to_xs_long(endPos);
+ theCurPos = theStartPos - 1;
}
catch (std::range_error& e)
{
@@ -294,17 +331,61 @@
}
+/*******************************************************************************
+
+********************************************************************************/
SimpleLazyTempSeqIter::~SimpleLazyTempSeqIter()
{
}
+/*******************************************************************************
+
+********************************************************************************/
+void SimpleLazyTempSeqIter::init(const store::TempSeq_t& seq)
+{
+ ZORBA_ASSERT(false);
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+void SimpleLazyTempSeqIter::init(
+ const store::TempSeq_t& seq,
+ xs_integer startPos,
+ xs_integer endPos)
+{
+ assert(seq->isLazy());
+
+ theTempSeq = static_cast<SimpleLazyTempSeq*>(seq.getp());
+
+ try
+ {
+ theStartPos = to_xs_long(startPos);
+ theEndPos = to_xs_long(endPos);
+ theCurPos = theStartPos - 1;
+ }
+ catch (std::range_error& e)
+ {
+ RAISE_ERROR_NO_LOC(zerr::ZSTR0060_RANGE_EXCEPTION,
+ ERROR_PARAMS(BUILD_STRING("sequence too big (" << e.what() << ")")));
+ }
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
void SimpleLazyTempSeqIter::open()
{
theCurPos = theStartPos - 1;
}
+/*******************************************************************************
+
+********************************************************************************/
bool SimpleLazyTempSeqIter::next(store::Item_t& result)
{
if (theCurPos < theEndPos && theTempSeq->containsItem(xs_integer(theCurPos+1)))
@@ -320,12 +401,18 @@
}
+/*******************************************************************************
+
+********************************************************************************/
void SimpleLazyTempSeqIter::reset()
{
theCurPos = theStartPos - 1;
}
+/*******************************************************************************
+
+********************************************************************************/
void SimpleLazyTempSeqIter::close()
{
}
=== modified file 'src/store/naive/simple_lazy_temp_seq.h'
--- src/store/naive/simple_lazy_temp_seq.h 2012-07-11 04:46:41 +0000
+++ src/store/naive/simple_lazy_temp_seq.h 2012-07-12 14:52:27 +0000
@@ -35,25 +35,38 @@
/*******************************************************************************
- theIterator : The input iterator that produces the items to be buffered by
- "this" temp sequence.
- theCopy : Whether or not to copy the items returned by theIterator
- before buffering them in "this" temp sequence.
- theMatFinished : Set to true when theIterator returns its last item.
- thePurgedUpTo : The number of items that have been purged from the buffer so
- far.
-
- theItems : Vector storing the buffered items.
+
+ theIterator :
+ -------------
+ The input iterator that produces the items to be cached by "this" temp sequence.
+
+ theMatFinished :
+ ----------------
+ Set to true when theIterator returns its last item.
+
+ thePurgedUpTo :
+ ---------------
+ The number of items that have been purged from the buffer so far.
+
+ theItems :
+ ----------
+ Vector storing the cached items.
********************************************************************************/
class SimpleLazyTempSeq : public store::TempSeq
{
private:
store::Iterator_t theIterator;
- bool theCopy;
+
bool theMatFinished;
+
xs_long thePurgedUpTo;
- std::vector<store::Item_t> theItems;
+ std::vector<store::Item*> theItems; // ref-counting is done manually
+
+ private:
+ void clear();
+
+ void matNextItem();
public:
SimpleLazyTempSeq() { }
@@ -62,38 +75,34 @@
virtual ~SimpleLazyTempSeq();
+ // Store API
+
+ bool isLazy() const { return true; }
+
+ bool empty();
+
+ xs_integer getSize() const;
+
void init(const store::Iterator_t& iter);
void append(const store::Iterator_t& iter);
void purge();
- void purgeUpTo(xs_integer upTo);
-
- bool empty();
-
- void getItem(xs_integer position, store::Item_t& result);
-
- bool containsItem(xs_integer position);
-
- xs_integer getSize() const;
+ void purgeUpTo(xs_integer pos);
+
+ void getItem(xs_integer pos, store::Item_t& result);
+
+ bool containsItem(xs_integer pos);
store::Iterator_t getIterator() const;
-
- store::Iterator_t getIterator(
- xs_integer startPos,
- xs_integer endPos,
- bool streaming = false) const;
-
- private:
- void matNextItem();
};
/*******************************************************************************
********************************************************************************/
-class SimpleLazyTempSeqIter : public store::Iterator
+class SimpleLazyTempSeqIter : public store::TempSeqIterator
{
private:
SimpleLazyTempSeq_t theTempSeq;
@@ -103,16 +112,27 @@
xs_long theEndPos;
public:
+ SimpleLazyTempSeqIter();
+
SimpleLazyTempSeqIter(
- const SimpleLazyTempSeq* aTempSeq,
- xs_integer aStartPos,
- xs_integer aEndPos);
+ const SimpleLazyTempSeq* tempSeq,
+ xs_integer startPos,
+ xs_integer endPos);
virtual ~SimpleLazyTempSeqIter();
+ // Store API
+
+ void init(const store::TempSeq_t& seq);
+
+ void init(const store::TempSeq_t& seq, xs_integer startPos, xs_integer endPos);
+
void open();
+
bool next(store::Item_t& result);
+
void reset();
+
void close();
};
=== modified file 'src/store/naive/simple_temp_seq.cpp'
--- src/store/naive/simple_temp_seq.cpp 2012-07-11 04:46:41 +0000
+++ src/store/naive/simple_temp_seq.cpp 2012-07-12 14:52:27 +0000
@@ -30,6 +30,16 @@
/*******************************************************************************
********************************************************************************/
+SimpleTempSeq::SimpleTempSeq(store::Item_t& item)
+{
+ theItems.push_back(NULL);
+ theItems[0] = item.release();
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
SimpleTempSeq::SimpleTempSeq(std::vector<store::Item_t>& items)
{
theItems.resize(items.size());
@@ -47,6 +57,15 @@
/*******************************************************************************
********************************************************************************/
+SimpleTempSeq::SimpleTempSeq(const store::Iterator_t& iter)
+{
+ init(iter);
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
SimpleTempSeq::~SimpleTempSeq()
{
clear();
@@ -108,13 +127,14 @@
********************************************************************************/
void SimpleTempSeq::purge()
{
+ clear();
}
/*******************************************************************************
********************************************************************************/
-void SimpleTempSeq::purgeUpTo(xs_integer upTo)
+void SimpleTempSeq::purgeUpTo(xs_integer pos)
{
}
@@ -196,51 +216,46 @@
}
-/*******************************************************************************
- Returns an iterator which reads just a part of the underlying TempSeq
-
- @param startPos The first item which the iterator returns
- @param endPos The last item which the iterator returns
- @return Iterator
-********************************************************************************/
-store::Iterator_t SimpleTempSeq::getIterator(
- xs_integer startPos,
- xs_integer endPos,
- bool streaming) const
-{
- return new SimpleTempSeqIter(this, startPos, endPos);
-}
+/////////////////////////////////////////////////////////////////////////////////
+// //
+// SimpleTempSeqIter //
+// //
+/////////////////////////////////////////////////////////////////////////////////
/*******************************************************************************
********************************************************************************/
-SimpleTempSeqIter::SimpleTempSeqIter(const SimpleTempSeq* aTempSeq)
+SimpleTempSeqIter::SimpleTempSeqIter(const SimpleTempSeq* tempSeq)
:
- theTempSeq(const_cast<SimpleTempSeq*>(aTempSeq)),
- theBorderType(none)
-{
- theBegin = theTempSeq->theItems.begin();
- theEnd = theTempSeq->theItems.end();
-}
-
-
-SimpleTempSeqIter::SimpleTempSeqIter(
- const SimpleTempSeq* seq,
- xs_integer startPos,
- xs_integer endPos)
-{
- init(const_cast<SimpleTempSeq*>(seq), startPos, endPos);
-}
-
-
+ theTempSeq(const_cast<SimpleTempSeq*>(tempSeq))
+{
+ theBegin = theTempSeq->theItems.begin();
+ theEnd = theTempSeq->theItems.end();
+}
+
+
+/*******************************************************************************
+
+********************************************************************************/
+void SimpleTempSeqIter::init(const store::TempSeq_t& tempSeq)
+{
+ theTempSeq = tempSeq;
+
+ theBegin = theTempSeq->theItems.begin();
+ theEnd = theTempSeq->theItems.end();
+}
+
+
+/*******************************************************************************
+ Return the items in the subrange [startPos, endPos]
+********************************************************************************/
void SimpleTempSeqIter::init(
- const store::TempSeq_t& aTempSeq,
+ const store::TempSeq_t& tempSeq,
xs_integer startPos,
xs_integer endPos)
{
- theTempSeq = aTempSeq;
- theBorderType = startEnd;
+ theTempSeq = tempSeq;
xs_long start;
xs_long end;
@@ -269,22 +284,18 @@
}
-void SimpleTempSeqIter::init(const store::TempSeq_t& aTempSeq)
-{
- theTempSeq = aTempSeq;
- theBorderType = none;
-
- theBegin = theTempSeq->theItems.begin();
- theEnd = theTempSeq->theItems.end();
-}
-
-
+/*******************************************************************************
+
+********************************************************************************/
void SimpleTempSeqIter::open()
{
theIte = theBegin;
}
+/*******************************************************************************
+
+********************************************************************************/
bool SimpleTempSeqIter::next(store::Item_t& result)
{
if (theIte != theEnd)
@@ -299,29 +310,23 @@
}
-store::Item* SimpleTempSeqIter::next()
-{
- if (theIte != theEnd)
- {
- store::Item* result = *theIte;
- ++theIte;
- return result;
- }
-
- return NULL;
-}
-
-
+/*******************************************************************************
+
+********************************************************************************/
void SimpleTempSeqIter::reset()
{
theIte = theBegin;
}
+/*******************************************************************************
+
+********************************************************************************/
void SimpleTempSeqIter::close()
{
}
+
} // namespace store
} // namespace zorba
/* vim:set et sw=2 ts=2: */
=== modified file 'src/store/naive/simple_temp_seq.h'
--- src/store/naive/simple_temp_seq.h 2012-07-11 04:46:41 +0000
+++ src/store/naive/simple_temp_seq.h 2012-07-12 14:52:27 +0000
@@ -23,9 +23,7 @@
namespace zorba { namespace simplestore {
-/**
- *
- */
+
typedef rchandle<class SimpleTempSeq> SimpleTempSeq_t;
@@ -46,21 +44,22 @@
public:
SimpleTempSeq() { }
- SimpleTempSeq(store::Item_t& item)
- {
- theItems.push_back(NULL);
- theItems[0] = item.release();
- }
+ SimpleTempSeq(store::Item_t& item);
SimpleTempSeq(std::vector<store::Item_t>& items);
- SimpleTempSeq(const store::Iterator_t& iter)
- {
- init(iter);
- }
+ SimpleTempSeq(const store::Iterator_t& iter);
virtual ~SimpleTempSeq();
+ // Store API
+
+ bool isLazy() const { return false; }
+
+ bool empty();
+
+ xs_integer getSize() const;
+
void init(const store::Iterator_t& iter);
void append(const store::Iterator_t& iter);
@@ -69,20 +68,11 @@
void purgeUpTo(xs_integer upTo);
- bool empty();
-
- xs_integer getSize() const;
-
void getItem(xs_integer position, store::Item_t& res);
bool containsItem(xs_integer position);
store::Iterator_t getIterator() const;
-
- store::Iterator_t getIterator(
- xs_integer startPos,
- xs_integer endPos,
- bool streaming = false) const;
};
@@ -92,14 +82,7 @@
class SimpleTempSeqIter : public store::TempSeqIterator
{
private:
- enum BorderType
- {
- none,
- startEnd
- };
-
SimpleTempSeq_t theTempSeq;
- BorderType theBorderType;
std::vector<store::Item*>::iterator theIte;
std::vector<store::Item*>::iterator theBegin;
@@ -110,19 +93,20 @@
SimpleTempSeqIter(const SimpleTempSeq* seq);
- SimpleTempSeqIter(const SimpleTempSeq* seq, xs_integer startPos, xs_integer endPos);
-
~SimpleTempSeqIter() {}
+ // Store API
+
void init(const store::TempSeq_t& seq);
void init(const store::TempSeq_t& seq, xs_integer startPos, xs_integer endPos);
- store::Item* next();
-
void open();
+
bool next(store::Item_t& result);
+
void reset();
+
void close();
};
Follow ups