zoukankan      html  css  js  c++  java
  • C/C++:Windows编程—调用DLL程序的2种方法(转载)

    文章为转载,原文出处https://blog.csdn.net/qq_29542611/article/details/86618902

    前言
    先简单介绍下DLL。DLL:Dynamic Link Library 动态链接库 是一个被其他应用程序调用的程序模块,其中封装了可以被调用的资源或函数。DLL 文件属于可执行文件,它符合Windows系统的PE文件格式,不过它是依附于EXE文件创建的的进程来执行的,不能单独运行。为了演示调用DLL程序的2种方法,我们先建一个简单的DLL程序。

    建一个简单的DLL程序
    IDE 使用vs2015,新建工程DLLTest1,选择空项目,创建完毕 右击项目 -> 属性 -> 常规 -> 配置类型 选择 动态库.dll。还是上一张图吧。

    添加头文件Calc.h 在头文件中添加导出函数add函数

    #pragma once
    
    extern "C" __declspec(dllexport) int add(int a, int b);
    

    cpp文件中进行实现  

    #include "Calc.h"
    
    int add(int a, int b)
    {
    	return a + b;
    }
    

    生成解决方案,在Debug下生成 DLLTest1.dll和DLLTest1.lib  

    对DLL程序调用方式一

    同样是新建空项目,添加main.cpp文件,将 DLLTest1.dll和DLLTest1.lib 拷贝到工程代码目录,然后项目添加添加现有项。项目目录如下
    在这里插入图片描述

     

    使用代码如下:

    #include <stdio.h>
    #include <stdlib.h>
    #include <Windows.h>
    
    #pragma comment(lib,"DLLTest1.lib")
    
    extern "C" int add(int a, int b);
    
    // 静态调用DLL库
    void StaticUse()
    {
    	int sum = add(10, 20);
    	printf("静态调用,sum = %d
    ", sum);
    }
    

    方式一 是静态调用,在连接阶段 将DLL库信息编写到EXE文件中,当调用DLL库中的函数是会加重DLL库。#pragma comment(lib,“DLLTest1”)告诉连机器需要在FirstDll.lib文件中找到DLL中导出函数的信息。  

    对DLL程序调用方式二

    方法一属于静态调用,其方式是通过链接器将DLL函数的导出函数写进可执行文件。现在使用第二种方式,相对前一种 是动态调用。动态调用不是链接时完成的,而是在运行时完成的。动态调用不会在可执行文件中写入DLL相关的信息。代码如下:

    // 动态调用DLL库
    void DynamicUse()
    {
        // 运行时加载DLL库
    	HMODULE module = LoadLibrary("DLLTest1.dll");
    	if (module == NULL)
    	{
    		printf("加载DLLTest1.dll动态库失败
    ");
    		return;
    	}
    	typedef int(*AddFunc)(int, int); // 定义函数指针类型
    	AddFunc add; 
        // 导出函数地址
    	add = (AddFunc)GetProcAddress(module, "add");
    
    	int sum  = add(100, 200);
    	printf("动态调用,sum = %d
    ",sum);
    }
    

    用到了以下2个函数:  

    // 根据DLL文件名 加载DLL
    // suc,返回一个模块句柄
    HMODULE WINAPI LoadLibrary(
      _In_ LPCTSTR lpFileName
    );
    // suc,返回lpProcName指向的函数名的函数地址。
    FARPROC GetProcAddress(
      HMODULE hModule,
      LPCSTR  lpProcName
    );
    

    测试

    测试代码如下:

    #include <stdio.h>
    #include <stdlib.h>
    #include <Windows.h>
    
    #pragma comment(lib,"DLLTest1.lib")
    
    extern "C" int add(int a, int b);
    
    // 静态调用DLL库
    void StaticUse()
    {
    	int sum = add(10, 20);
    	printf("静态调用,sum = %d
    ", sum);
    }
    
    // 动态调用DLL库
    void DynamicUse()
    {
    	HMODULE module = LoadLibrary("DLLTest1.dll");
    	if (module == NULL)
    	{
    		printf("加载DLLTest1.dll动态库失败
    ");
    		return;
    	}
    	typedef int(*AddFunc)(int, int); // 定义函数指针类型
    	AddFunc add;
    	add = (AddFunc)GetProcAddress(module, "add");
    
    	int sum = add(100, 200);
    	printf("动态调用,sum = %d
    ", sum);
    }
    
    int main(char argc, char* argv[])
    {
    	StaticUse();
    	DynamicUse();
    	system("pause");
    	return 0;
    }
    

    验证结果,和我们想象的一样。  

      

  • 相关阅读:
    spoj freetour II
    hdu5977 Garden of Eden
    bzoj 1047 理想的正方形
    Python学习-22.Python中的函数——type
    Python学习-21.Python的代码注释
    Python学习-20.Python的Urllib模块
    Python学习-19.Python的Http模块
    Python学习-18.Python中的错误处理(三)
    Python学习-17.Python中的错误处理(二)
    Python学习-16.Python中的错误处理
  • 原文地址:https://www.cnblogs.com/nxopen2018/p/11188329.html
Copyright © 2011-2022 走看看