• PostgreSQL在何处处理 sql查询之三十八


    这里又遇到了函数指针:

    executor.h头文件中,定义了 ExecScanAccessMtd 指针,或者定义了一个ExecScanAccessMtd 函数原型的指针

    /*
     * prototypes from functions in execScan.c
     */
    typedef TupleTableSlot *(*ExecScanAccessMtd) (ScanState *node);

    之后,在NodeSeqScan.c处有一个实现:

    /* ----------------------------------------------------------------
     *        SeqNext
     *
     *        This is a workhorse for ExecSeqScan
     * ----------------------------------------------------------------
     */
    static TupleTableSlot *
    SeqNext(SeqScanState *node)
    {
        HeapTuple    tuple;
        HeapScanDesc scandesc;
        EState       *estate;
        ScanDirection direction;
        TupleTableSlot *slot;
    
        /*
         * get information from the estate and scan state
         */
        scandesc = node->ss_currentScanDesc;
        estate = node->ps.state;
        direction = estate->es_direction;
        slot = node->ss_ScanTupleSlot;
    
        /*
         * get the next tuple from the table
         */
        tuple = heap_getnext(scandesc, direction);
    
        /*
         * save the tuple and the buffer returned to us by the access methods in
         * our scan tuple slot and return the slot.  Note: we pass 'false' because
         * tuples returned by heap_getnext() are pointers onto disk pages and were
         * not created with palloc() and so should not be pfree()'d.  Note also
         * that ExecStoreTuple will increment the refcount of the buffer; the
         * refcount will not be dropped until the tuple table slot is cleared.
         */
        if (tuple)
            ExecStoreTuple(tuple,    /* tuple to store */
                           slot,    /* slot to store in */
                           scandesc->rs_cbuf,        /* buffer associated with this
                                                     * tuple */
                           false);    /* don't pfree this pointer */
        else
            ExecClearTuple(slot);
    
        return slot;
    }

    之后,在下列方法中, 把函数指针当作参数进行传递:

    TupleTableSlot *
    ExecScan(ScanState *node,
             ExecScanAccessMtd accessMtd,    /* function returning a tuple */
             ExecScanRecheckMtd recheckMtd)
    {
       ...
    }

    调用:

    TupleTableSlot *
    ExecSeqScan(SeqScanState *node)
    {
        return ExecScan((ScanState *) node,
                        (ExecScanAccessMtd) SeqNext,
                        (ExecScanRecheckMtd) SeqRecheck);
    }
  • 相关阅读:
    Mysql开启日志
    amfphp传递负数的bug
    linux /var/spool/clientmqueue 目录占大量空间
    WinXP SSH连接不上虚拟机的解决方法
    批量数据替换助手V1.0版发布
    也谈反射的应用场景
    反射+特性打造简洁的AJAX调用
    文本处理之利器正则表达式闪亮登场
    关于缩略图的生成与访问策略的一些经验分享
    装饰模式个人的一些理解
  • 原文地址:https://www.cnblogs.com/gaojian/p/3110306.html
Copyright © 2020-2023  润新知