zoukankan      html  css  js  c++  java
  • 工程化编程实战callback接口学习笔记

    作业要求

    • 在VSCode下编译运行lab5-1.tar.gz 即http://pan.baidu.com/s/1pJ0qAIv

    • 通过VSCode+GDB调试程序找出quit命令无法运行的bug产生的原因

    • 分析callback接口的运行机制,总结callback接口设计的方法

    具体实现

    1. 环境准备

    1. 首先安装MAC环境下的GCC

    2. 打开VSCode,通过Ctrl+Shift+x 安装C/C++调试器

    3. 下载作业要求中的lab5-1.tar.gz文件

    2. 文件运行

    1. 打开VSCode命令行,使用如下命令编译程序,生成可执行文件
    gcc -o test menu.c linktable.c
    

    结果如下:

    根据提示发现文件缺少函数strcmp所在的头文件,在menu.c中添加string.h头文件,继续编译后

    1. 编译成功,执行编译后文件,输入指令./test,进一步输入help和quit指令,结果如下:

    3. 调试

    1. 定位main函数,代码如下:
    int main()
    {
        InitMenuData(&head); 
       /* cmd line begins */
        while(1)
        {
            printf("Input a cmd number > ");
            scanf("%s", cmd);
            tDataNode *p = FindCmd(head, cmd);
            if( p == NULL)
            {
                printf("This is a wrong cmd!
     ");
                continue;
            }
            printf("%s - %s
    ", p->cmd, p->desc); 
            if(p->handler != NULL) 
            { 
                p->handler();
            }
       
        }
    }
    
    

    发现通过调用FindCmd()函数进行指令具体操作,进一步找到该函数的调用函数如下:

    tLinkTableNode * SearchLinkTableNode(tLinkTable *pLinkTable, int Conditon(tLinkTableNode * pNode))
    {
        if(pLinkTable == NULL || Conditon == NULL)
        {
            return NULL;
        }
    //部分代码
    

    我们能够看到,调用该查找函数传入的参数为InitMenuData(&head)链表和我们输入的cmd命令,我们来检查一下直接返回空指针只有在pLinkTable和Conditon至少有一个为空的时候,很明显这是我们的输入和cmd命令,并不为空,让我们继续看另外一种情况

    //承接上部分代码 
    while(pNode != pLinkTable->pTail)
        {   
            if(Conditon(pNode) == SUCCESS)
            {
                return pNode;                   
            }
            pNode = pNode->pNext;
        }
        return NULL;
    }
    

    另一种情况就是直到pNode循环遍历结束以后也未满足Conditon(pNode) == SUCCESS的条件,那么我们来看看pLinkTable->pTai

     else
        {
            pLinkTable->pTail->pNext = pNode;
            pLinkTable->pTail = pNode;
        }
        pLinkTable->SumOfNode += 1 ;
        pthread_mutex_unlock(&(pLinkTable->mutex));
        return SUCCESS;  
    

    不难发现,在判断是否为末尾的时候并未判断Conditon(pNode) == SUCCESS,而直接返回空指针,我们将SearchLinkTableNode函数修改如下(改为判断只有不为空的时候才进行遍历):

    tLinkTableNode * SearchLinkTableNode(tLinkTable *pLinkTable, int Conditon(tLinkTableNode * pNode))
    {
        if(pLinkTable == NULL || Conditon == NULL)
        {
            return NULL;
        }
        tLinkTableNode * pNode = pLinkTable->pHead;
        while(pNode != NULL)     
        {   
            if(Conditon(pNode) == SUCCESS)
            {
                return pNode;                   
            }
            pNode = pNode->pNext;
        }
        return NULL;
    }
    

    重新编译运行,结果如下:

    Callback接口

    当程序跑起来时,一般情况下,应用程序(application program)会时常通过API调用库里所预先备好的函数。但是有些库函数(library function)却要求应用先传给它一个函数,好在合适的时候调用,以完成目标任务。这个被传入的、后又被调用的函数就称为回调函数(callback function)。


    可以看到,回调函数通常和应用处于同一抽象层(因为传入什么样的回调函数是在应用级别决定的)。而回调就成了一个高层调用底层,底层再回过头来调用高层的过程。

  • 相关阅读:
    双指针
    二维数组 查找常用字符
    将数组分为相等的三部分
    交换 排序
    买股票
    双指针 回文数
    双指针
    测试SM图床
    cnpm,vue等命令不识别的问题废人解决方案
    typeof面试题解答
  • 原文地址:https://www.cnblogs.com/xshun/p/12520776.html
Copyright © 2011-2022 走看看