• 一、思路

    Windows程序中,各个进程之间常常需要交换数据,进行数据通讯。常用的方法有

    • 使用内存映射文件
    • 通过共享内存DLL共享内存
    • 使用SendMessage向另一进程发送WM_COPYDATA消息

    比起前两种的复杂实现来,WM_COPYDATA消息无疑是一种经济实惠的一中方法。WM_COPYDATA消息的主要目的是允许在进程间传递只读数据。Windows在通过WM_COPYDATA消息传递期间,不提供继承同步方式。SDK文档推荐用户使用SendMessage函数,接受方在数据拷贝完成前不返回,这样发送方就不可能删除和修改数据:

    这个函数的原型及其要用到的结构如下:

    SendMessage(hwnd,WM_COPYDATA,wParam,lParam);

    其中,WM_COPYDATA对应的十六进制数为0x004AwParam设置为包含数据的窗口的句柄。lParam指向一个COPYDATASTRUCT的结构:

    typedef struct tagCOPYDATASTRUCT
    {
    DWORD dwData;//用户定义数据
    DWORD cbData;//数据大小
    PVOID lpData;//指向数据的指针
    } COPYDATASTRUCT;

    该结构用来定义用户数据。

    二、具体过程

    在发送方,用FindWindow找到接受方的句柄,然后向接受方发送WM_COPYDATA消息。

    在接受方,在DefWndProc事件中来处理这条消息。由于中文编码是两个字节,所以传递中文时候字节长度要搞清楚。

    发送方代码:

    using System;
    using System.Collections.Generic;
    using System.ComponentModel;
    using System.Data;
    using System.Drawing;
    using System.Linq;
    using System.Text;
    using System.Windows.Forms;
    using System.Runtime.InteropServices;
    namespace Client
    {
    public partial class FrmClient : Form
    {
    public FrmClient()
    {
    InitializeComponent();
    }
    private void FrmClient_Load(object sender, EventArgs e)
    {
    } [DllImport("User32.dll", EntryPoint = "SendMessage")]
    private static extern int SendMessage(
    int hWnd, // handle to destination window
    int Msg, // message
    int wParam, // first message parameter
    ref COPYDATASTRUCT lParam // second message parameter
    ); [DllImport("User32.dll", EntryPoint = "FindWindow")]
    private static extern int FindWindow(string lpClassName, string lpWindowName); public struct COPYDATASTRUCT
    {
    public IntPtr dwData;
    public int cbData;
    [MarshalAs(UnmanagedType.LPStr)]
    public string lpData;
    }
    const int WM_COPYDATA = 0x004A; private void btnSend_Click(object sender, EventArgs e)
    {
    int WINDOW_HANDLER = FindWindow(null, @"C#进程间通信(Server)");
    if (WINDOW_HANDLER != 0)
    {
    byte[] sarr = System.Text.Encoding.Default.GetBytes(this.textBox1.Text);
    int len = sarr.Length;
    COPYDATASTRUCT cds;
    cds.dwData = (IntPtr)100;
    cds.lpData = this.textBox1.Text;
    cds.cbData = len + 1;
    SendMessage(WINDOW_HANDLER, WM_COPYDATA, 0, ref cds);
    }
    }
    }
    }

    接收端代码:

    using System;
    using System.Collections.Generic;
    using System.ComponentModel;
    using System.Data;
    using System.Drawing;
    using System.Linq;
    using System.Text;
    using System.Windows.Forms;
    using System.Runtime.InteropServices;
    namespace Server
    {
    public partial class FrmServer : Form
    {
    public FrmServer()
    {
    InitializeComponent();
    }
    private void Form1_Load(object sender, EventArgs e)
    {
    } public struct COPYDATASTRUCT
    {
    public IntPtr dwData;
    public int cbData;
    [MarshalAs(UnmanagedType.LPStr)]
    public string lpData;
    }
    const int WM_COPYDATA = 0x004A;
    protected override void DefWndProc(ref System.Windows.Forms.Message m)
    {
    switch (m.Msg)
    {
    case WM_COPYDATA:
    COPYDATASTRUCT mystr = new COPYDATASTRUCT();
    Type mytype = mystr.GetType();
    mystr = (COPYDATASTRUCT)m.GetLParam(mytype);
    lblMsg.Text = "收到消息:" + mystr.lpData;
    MessageBox.Show ("收到消息:" + mystr.lpData);
    break;
    default:
    base.DefWndProc(ref m);
    break;
    }
    }
    }
    }

    三、相关资料

C#:进程之间传递数据的更多相关文章

  1. 用WM_COPYDATA消息来实现两个进程之间传递数据

    文着重讲述了如果用WM_COPYDATA消息来实现两个进程之间传递数据. 进程之间通讯的几种方法:在Windows程序中,各个进程之间常常需要交换数据,进行数据通讯.常用的方法有   1.使用内存映射 ...

  2. 使用RandomAccessFile在两个java进程之间传递数据

    大部分情况下,我们面对在两个java进程只见传递数据的问题时,第一个想到的就是开server,然后通过socket收发消息.这方面有大量的框架可用,就不细说了.但如果两个进程是在一台机器上,那么还可以 ...

  3. python进程之间修改数据[Manager]与进程池[Pool]

    #前面的队列Queue和管道Pipe都是仅仅能再进程之间传递数据,但是不能修改数据,今天我们学习的东西就可以在进程之间同时修改一份数据 #Mnager就可以实现 import multiprocess ...

  4. Activity之间传递数据的方式及常见问题总结

    Activity之间传递数据一般通过以下几种方式实现: 1. 通过intent传递数据 2. 通过Application 3. 使用单例 4. 静态成员变量.(可以考虑 WeakReferences) ...

  5. Python 进程之间共享数据

    最近遇到多进程共享数据的问题,到网上查了有几篇博客写的蛮好的,记录下来方便以后查看. 一.Python multiprocessing 跨进程对象共享  在mp库当中,跨进程对象共享有三种方式,第一种 ...

  6. Controller之间传递数据:属性传值

    在项目中,Controller之间传递数据非常之多,这里简单介绍一下属性传值.例如有FirstController 和 SecondController,数据从First传递到Second中,我们如何 ...

  7. Activity之间传递数据或数据包Bundle,传递对象,对象序列化,对象实现Parcelable接口

    package com.gaojinhua.android.activitymsg; import android.content.Intent; import android.os.Bundle; ...

  8. 28、activity之间传递数据&批量传递数据

    import android.app.Activity; import android.content.Intent; import android.os.Bundle; import android ...

  9. 【Android 复习】 : Activity之间传递数据的几种方式

    在Android开发中,我们通常需要在不同的Activity之间传递数据,下面我们就来总结一下在Activity之间数据传递的几种方式. 1. 使用Intent来传递数据 Intent表示意图,很多时 ...

  10. C#中使用SendMessage在进程间传递数据的实例

    原文:C#中使用SendMessage在进程间传递数据的实例 1 新建解决方案SendMessageExample 在解决方案下面新建三个项目:CopyDataStruct,Receiver和Send ...

随机推荐

  1. 用【Makefile】或【Cmake】编译【C/Fortran】程序文件

    一.vimrc文件设置 set tabstop=4 "tab空格4 set expandtab "将tab扩展成空格 set softtabstop=4 "表示在编辑模式 ...

  2. MPI学习笔记(四):矩阵相乘的Cannon卡农算法

    mpi矩阵乘法:C=αAB+βC 一.Cannon卡农算法基本介绍 1.二维矩阵串行乘法 两个n维方阵的乘法A×B=C的串行计算公式为: 下图是用图示来表示的这种计算规则: 2.二维块划分的思想 并行 ...

  3. TestMarkdown1

    VSCode 实时预览还需要执行 Markdown: Open Preview to the Side 命令来实现. 在命令窗口输入 Markdown: Open Preview to the Sid ...

  4. CompatTelRunner CPU 占用 22% win10 笔记本常常无故风扇狂转

    CompatTelRunner CPU 占用 22% win10 笔记本常常无故风扇狂转 CompatTelRunner.exe is also known as Windows Compatibil ...

  5. TiDB 多集群告警监控-初章-监控融合、自动告警处理

    author:longzhuquan 背景 随着公司XC改造步伐的前进,越来越多的业务选择 TiDB,由于各个业务之间需要物理隔离,避免不了的 TiDB 集群数量越来越多.虽然每套 TiDB 集群均有 ...

  6. 什么是 MyBatis 的接口绑定,有什么好处?

    接口映射就是在 MyBatis 中任意定义接口,然后把接口里面的方法和 SQL 语句绑定,我们直接调用接口方法就可以,这样比起原来了 SqlSession 提供的方法我们可以有更加灵活的选择和设置.

  7. Mysql行转列,列转行 WITH ROLLUP 统计

    Mysql行转列,列转行 WITH ROLLUP 统计 DROP TABLE IF EXISTS tb_score; CREATE TABLE tb_score( id INT(11) NOT NUL ...

  8. java关于json的一些问题

    今天重写代码的时候,发现了一个异常:java.lang.ClassNotFoundException: org.apache.commons.lang.exception.NestableRuntim ...

  9. Freertos学习:04-任务的调试函数

    --- title: rtos-freertos-04-任务的调试函数 EntryName: rtos-freertos-04-task-debug date: 2020-06-22 08:49:06 ...

  10. arm linux 移植 ffmpeg 库 + x264 + x265

    背景 Ffmpeg 中带有h264的解码,没有编码,需要添加x264.libx264是一个自由的H.264编码库,是x264项目的一部分,使用广泛,ffmpeg的H.264实现就是用的libx264. ...