zoukankan      html  css  js  c++  java
  • Windows动态链接库:dll与exe相互调用问题

    本文回顾学习一下Windows动态链接库:dll与exe相互调用问题。一般滴,exe用来调用dll中的类或函数,但是dll中也可以调用exe中的类或函数,本文做一些尝试总结。

    dll程序:

    Calculator.h 
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
     
    // Calculator.h: interface for the Calculator class.
    //
    //////////////////////////////////////////////////////////////////////

    #if !defined(AFX_ALCULATOR_H__D072BBB5_615B_45A9_9864_80C2291FA695__INCLUDED_)
    #define AFX_ALCULATOR_H__D072BBB5_615B_45A9_9864_80C2291FA695__INCLUDED_

    #if _MSC_VER > 1000
    #pragma once
    #endif // _MSC_VER > 1000


    class IHelper;
    class Helper;
    class _declspec(dllexport) Calculator
    {
    public:
        Calculator();
        ~Calculator();

        
    void registerHelper(IHelper *iHelper);
        
    void registerHelper(Helper  *helper);
        
        
    int add(int num1, int num2);
        
    int sub(int num1, int num2);
        
    private:
        IHelper     *m_iHelper;
        Helper      *m_helper;
        
    };

    extern "C" _declspec(dllexport) Calculator *getCalculator();

    #endif // !defined(AFX_ALCULATOR_H__D072BBB5_615B_45A9_9864_80C2291FA695__INCLUDED_)
     Calculator.cpp 
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
     
    // Calculator.cpp: implementation of the Calculator class.
    //
    //////////////////////////////////////////////////////////////////////

    #include "stdafx.h"
    #include "Calculator.h"
    #include "../vs_dll_caller/Helper.h"

    #include "../vs_dll_caller/Helper.h"

    //////////////////////////////////////////////////////////////////////
    // Construction/Destruction
    //////////////////////////////////////////////////////////////////////

    Calculator::Calculator()
    {
        
    }

    Calculator::~Calculator()
    {
        
    }

    void Calculator::registerHelper(IHelper *iHelper)
    {
        m_iHelper = iHelper;
    }

    void Calculator::registerHelper(Helper *helper)
    {
        m_helper = helper;
    }

    int Calculator::add(int num1, int num2)
    {
        m_iHelper->print(
    "do add!");
        
    return num1 + num2;
    }

    int Calculator::sub(int num1, int num2)
    {
        m_iHelper->print(
    "do sub!");
        
    return num1 >= num2 ? num1 - num2 : -1;
    }

    Calculator *getCalculator()
    {
        
    return new Calculator();
    }

    exe程序:

     IHelper.h
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
     
    #pragma once
    /************************************************************************/
    // 抽象类                                                               */
    // 该类在exe中,方便dll中调用
    /************************************************************************/


    class IHelper
    {
    public:
        
    virtual void print(const char *str) = 0;
    };
     Helper.h
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
     
    // Helper.h: interface for the Helper class.
    //
    //////////////////////////////////////////////////////////////////////

    #if !defined(AFX_HELPER_H__9234DC8C_56CC_4765_BDA6_276F30C52221__INCLUDED_)
    #define AFX_HELPER_H__9234DC8C_56CC_4765_BDA6_276F30C52221__INCLUDED_

    #if _MSC_VER > 1000
    #pragma once
    #endif // _MSC_VER > 1000

    #include "iHelper.h"

    class Helper
        : 
    public IHelper  
    {
    public:
        Helper();
        
    virtual ~Helper();

        
    virtual void print(const char *str);

    };

    #endif // !defined(AFX_HELPER_H__9234DC8C_56CC_4765_BDA6_276F30C52221__INCLUDED_)
     Helper.cpp
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
     
    // Helper.cpp: implementation of the Helper class.
    //
    //////////////////////////////////////////////////////////////////////

    #include "Helper.h"
    #include <iostream>

    //////////////////////////////////////////////////////////////////////
    // Construction/Destruction
    //////////////////////////////////////////////////////////////////////

    Helper::Helper()
    {

    }

    Helper::~Helper()
    {

    }

    void Helper::print(const char *str)
    {
        std::cout << str << 
    " ";
    }
     main.cpp
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
     
    #include <Windows.h>
    #include <tchar.h>
    #include <iostream>
    #include "Helper.h"
    #include "../vs_dll/Calculator.h"

    typedef Calculator*(*Cal)();

    int main()
    {
        std::cout << 
    "Hello World! ";

        
    // 隐式调用
        std::cout << " 隐式调用" << std::endl;
        Calculator cal;
        
    // 回调指针给dll
        IHelper *helper = new Helper();
        cal.registerHelper(helper);
        
    int num_add = cal.add(32);
        std::cout << 
    "cal.add = " << num_add << std::endl;
        
    int num_sub = cal.sub(32);
        std::cout << 
    "cal.sub = " << num_sub << std::endl;

        
    // 显式调用
        std::cout << " 显式调用" << std::endl;
        HMODULE hDll = ::LoadLibrary(
    "../Debug/vs_dll.dll");
        
    if (hDll != NULL)
        {
            Cal cal = (Cal)GetProcAddress(hDll, 
    "getCalculator");
            Calculator *pCal = cal();
            
    // 回调指针给dll
            IHelper *helper = new Helper();
            pCal->registerHelper(helper);
            
    int num_add = pCal->add(32);
            std::cout << 
    "pCal->add = " << num_add << std::endl;
            
    int num_sub = pCal->sub(32);
            std::cout << 
    "pCal->sub = " << num_sub << std::endl;

        }

        std::cin.get();
        
    return 0;
    }

    总结:一般滴,dll是用来被exe调用的,如果dll要调用exe中的类,可以给dll注册一个该类的指针即可,而且该指针为抽象类指针。

  • 相关阅读:
    设计模式
    LiggEasyWinApp-104-Ligg.EasyWinForm:Zone
    Ligg.EasyWinApp-10300-Ligg.EasyWinForm:View的配置
    LiggEasyWinApp-103-Ligg.EasyWinForm:View
    Ligg.EasyWinApp-102-Ligg.EasyWinForm:Function--ControlBox、Tray、Resize、Menu
    Ligg.EasyWinApp-101-Ligg.EasyWinForm: Application--启动,传入参数、读取Application级别配置文件、验证密码、软件封面、启动登录、StartForm
    Ligg.EasyWinApp-100-Ligg.EasyWinForm:一款Winform应用编程框架和UI库介绍
    Ligg.WinOa-000: Windows运维自动化编程实战--前言
    Ligg.EasyWinApp-000: 一款Windows应用编程框架介绍
    微服务分布式 spring cloud springboot 框架源码 activiti工作流 前后分离
  • 原文地址:https://www.cnblogs.com/MakeView660/p/11654766.html
Copyright © 2011-2022 走看看