Header And Logo

| The world's most advanced open source database.


nodeUnique.c File Reference

#include "postgres.h"
#include "executor/executor.h"
#include "executor/nodeUnique.h"
#include "utils/memutils.h"
Include dependency graph for nodeUnique.c:

Go to the source code of this file.


TupleTableSlotExecUnique (UniqueState *node)
UniqueStateExecInitUnique (Unique *node, EState *estate, int eflags)
void ExecEndUnique (UniqueState *node)
void ExecReScanUnique (UniqueState *node)

Function Documentation

void ExecEndUnique ( UniqueState node  ) 
UniqueState* ExecInitUnique ( Unique node,
EState estate,
int  eflags 

Definition at line 112 of file nodeUnique.c.

References ALLOCSET_DEFAULT_INITSIZE, ALLOCSET_DEFAULT_MAXSIZE, ALLOCSET_DEFAULT_MINSIZE, AllocSetContextCreate(), Assert, CurrentMemoryContext, UniqueState::eqfunctions, EXEC_FLAG_BACKWARD, EXEC_FLAG_MARK, ExecAssignResultTypeFromTL(), ExecInitNode(), ExecInitResultTupleSlot(), execTuplesMatchPrepare(), makeNode, Unique::numCols, outerPlan, outerPlanState, PlanState::plan, UniqueState::ps, PlanState::ps_ProjInfo, PlanState::state, UniqueState::tempContext, and Unique::uniqOperators.

Referenced by ExecInitNode().

    UniqueState *uniquestate;

    /* check for unsupported flags */
    Assert(!(eflags & (EXEC_FLAG_BACKWARD | EXEC_FLAG_MARK)));

     * create state structure
    uniquestate = makeNode(UniqueState);
    uniquestate->ps.plan = (Plan *) node;
    uniquestate->ps.state = estate;

     * Miscellaneous initialization
     * Unique nodes have no ExprContext initialization because they never call
     * ExecQual or ExecProject.  But they do need a per-tuple memory context
     * anyway for calling execTuplesMatch.
    uniquestate->tempContext =

     * Tuple table initialization
    ExecInitResultTupleSlot(estate, &uniquestate->ps);

     * then initialize outer plan
    outerPlanState(uniquestate) = ExecInitNode(outerPlan(node), estate, eflags);

     * unique nodes do no projections, so initialize projection info for this
     * node appropriately
    uniquestate->ps.ps_ProjInfo = NULL;

     * Precompute fmgr lookup data for inner loop
    uniquestate->eqfunctions =

    return uniquestate;

void ExecReScanUnique ( UniqueState node  ) 

Definition at line 187 of file nodeUnique.c.

References PlanState::chgParam, ExecClearTuple(), ExecReScan(), PlanState::lefttree, NULL, UniqueState::ps, and PlanState::ps_ResultTupleSlot.

Referenced by ExecReScan().

    /* must clear result tuple so first input tuple is returned */

     * if chgParam of subnode is not null then plan will be re-scanned by
     * first ExecProcNode.
    if (node->ps.lefttree->chgParam == NULL)

TupleTableSlot* ExecUnique ( UniqueState node  ) 

Definition at line 46 of file nodeUnique.c.

References UniqueState::eqfunctions, ExecClearTuple(), ExecCopySlot(), ExecProcNode(), execTuplesMatch(), Unique::numCols, outerPlan, outerPlanState, PlanState::plan, UniqueState::ps, PlanState::ps_ResultTupleSlot, UniqueState::tempContext, TupIsNull, and Unique::uniqColIdx.

Referenced by ExecProcNode().

    Unique     *plannode = (Unique *) node->ps.plan;
    TupleTableSlot *resultTupleSlot;
    TupleTableSlot *slot;
    PlanState  *outerPlan;

     * get information from the node
    outerPlan = outerPlanState(node);
    resultTupleSlot = node->ps.ps_ResultTupleSlot;

     * now loop, returning only non-duplicate tuples. We assume that the
     * tuples arrive in sorted order so we can detect duplicates easily. The
     * first tuple of each group is returned.
    for (;;)
         * fetch a tuple from the outer subplan
        slot = ExecProcNode(outerPlan);
        if (TupIsNull(slot))
            /* end of subplan, so we're done */
            return NULL;

         * Always return the first tuple from the subplan.
        if (TupIsNull(resultTupleSlot))

         * Else test if the new tuple and the previously returned tuple match.
         * If so then we loop back and fetch another new tuple from the
         * subplan.
        if (!execTuplesMatch(slot, resultTupleSlot,
                             plannode->numCols, plannode->uniqColIdx,

     * We have a new tuple different from the previous saved tuple (if any).
     * Save it and return it.  We must copy it because the source subplan
     * won't guarantee that this source tuple is still accessible after
     * fetching the next source tuple.
    return ExecCopySlot(resultTupleSlot, slot);