C# Socket 入门5 UPD 结构体 与 C++ 通信

2023-10-07 18:08

本文主要是介绍C# Socket 入门5 UPD 结构体 与 C++ 通信,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

C# Socket 入门5 UPD 结构体 与 C++ 通信

1. 同样, 我们先看看这一个比简单的 结构体

代码
using  System;
using  System.Collections.Generic;
using  System.Text;
using  System.Runtime.InteropServices;

namespace  CSharp_Socket_5
{
    
///   <summary>
    
///  通信消息格式
    
///   </summary>
    [Serializable]
    [StructLayout(LayoutKind.Sequential, Pack 
=   1 )]
    
public   struct  CP2PMessage
    {
        
public   ushort  id;
    }
}

 

 

C++ 版本

struct  CP2PMessage
{
    WORD id;
};

 

 

2. C# 服务端,  和之前的一样滴~~  看来是不是很亲切也~

代码
using  System;
using  System.Collections.Generic;
using  System.Text;
using  System.Net.Sockets;
using  System.Net;
using  System.Runtime.InteropServices;

namespace  CSharp_Socket_5
{
    
class  Program
    {
        
///   <summary>
        
///  服务端
        
///   </summary>
        
///   <param name="args"></param>
         static   void  Main( string [] args)
        {
            
//  1.创建套节字
            Socket socket  =   new  Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp);

            
//  2.填充IP
            IPEndPoint ipe  =   new  IPEndPoint(IPAddress.Any,  4321 );

            
//  3.绑定
            socket.Bind(ipe);

            
//  等待客户机连接
            Console.WriteLine( " 这个服务器, host name is {0} " , Dns.GetHostName());
            Console.WriteLine(
" 等待客户端连接.... " );

            
//  4.得客户机IP
            IPEndPoint sender  =   new  IPEndPoint(IPAddress.Any,  0 );
            EndPoint remote 
=  (EndPoint)sender;

            
//  5.接收客户机数据
             byte [] buffer  =   new   byte [ 1024 ];
            socket.ReceiveFrom(buffer, 
ref  remote);

            CP2PMessage msg 
=   new  CP2PMessage();
            msg 
=  (CP2PMessage)BytesToStruct(buffer, msg.GetType());

            Console.WriteLine(
" 接C++收的值为:{0} " , msg.id);

            Console.ReadKey();

        }

        
public   static   byte [] StructToBytes( object  obj)
        {
            
int  size  =  Marshal.SizeOf(obj);
            
byte [] bytes  =   new   byte [size];
            IntPtr structPtr 
=  Marshal.AllocHGlobal(size);  // 分配结构体大小的内存空间
            Marshal.StructureToPtr(obj, structPtr,  false );  // 将结构体拷到分配好的内存空间
            Marshal.Copy(structPtr, bytes,  0 , size);        // 从内存空间拷到byte数组
            Marshal.FreeHGlobal(structPtr);                 // 释放内存空间
             return  bytes;
        }

        
public   static   object  BytesToStruct( byte [] bytes, Type type)
        {
            
int  size  =  Marshal.SizeOf(type);
            
if  (size  >  bytes.Length)
                
return   null ;
            IntPtr structPtr 
=  Marshal.AllocHGlobal(size);  // 分配结构大小的内存空间
            Marshal.Copy(bytes,  0 , structPtr, size);        // 将byte数组拷到分配好的内存空间
             object  obj  =  Marshal.PtrToStructure(structPtr, type);
            Marshal.FreeHGlobal(structPtr);
            
return  obj;
        }
    }
}

 

 

3. 重点了,,C++ 客户端

代码
#include  < winsock2.h >
#include 
< stdio.h >
#pragma  comment(lib, "WS2_32.lib")

struct  CP2PMessage
{
    WORD id;
};

void  main()
{
    
// 初始化 WS2_32.dll
    WSADATA wsaData;
    ::WSAStartup(MAKEWORD(
2 , 2 ),  &  wsaData);

    
//  1.创建套节字
    SOCKET s  =  ::socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);

    
//  2.填写服务器IP
    sockaddr_in sin;
    sin.sin_family 
=  AF_INET;
    sin.sin_port 
=  ::htons( 4321 );
    sin.sin_addr.S_un.S_addr 
=  ::inet_addr( " 127.0.0.1 " );

    
//  3. 向服务器发送消息
    CP2PMessage msg;
    msg.id 
=   10 ;

    ::sendto(s, (
char * ) & msg,  sizeof (msg),  0 , (sockaddr * ) & sin,  sizeof (sin));
}

 

 

4. 完成了,,,这么, 请看效果图!!

这篇关于C# Socket 入门5 UPD 结构体 与 C++ 通信的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/159509

相关文章

C#中checked关键字的使用小结

《C#中checked关键字的使用小结》本文主要介绍了C#中checked关键字的使用,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学... 目录✅ 为什么需要checked? 问题:整数溢出是“静默China编程”的(默认)checked的三种用

C#中预处理器指令的使用小结

《C#中预处理器指令的使用小结》本文主要介绍了C#中预处理器指令的使用,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧... 目录 第 1 名:#if/#else/#elif/#endif✅用途:条件编译(绝对最常用!) 典型场景: 示例

C#实现将XML数据自动化地写入Excel文件

《C#实现将XML数据自动化地写入Excel文件》在现代企业级应用中,数据处理与报表生成是核心环节,本文将深入探讨如何利用C#和一款优秀的库,将XML数据自动化地写入Excel文件,有需要的小伙伴可以... 目录理解XML数据结构与Excel的对应关系引入高效工具:使用Spire.XLS for .NETC

C++ 右值引用(rvalue references)与移动语义(move semantics)深度解析

《C++右值引用(rvaluereferences)与移动语义(movesemantics)深度解析》文章主要介绍了C++右值引用和移动语义的设计动机、基本概念、实现方式以及在实际编程中的应用,... 目录一、右值引用(rvalue references)与移动语义(move semantics)设计动机1

C#如何在Excel文档中获取分页信息

《C#如何在Excel文档中获取分页信息》在日常工作中,我们经常需要处理大量的Excel数据,本文将深入探讨如何利用Spire.XLSfor.NET,高效准确地获取Excel文档中的分页信息,包括水平... 目录理解Excel中的分页机制借助 Spire.XLS for .NET 获取分页信息为什么选择 S

C#高效实现在Word文档中自动化创建图表的可视化方案

《C#高效实现在Word文档中自动化创建图表的可视化方案》本文将深入探讨如何利用C#,结合一款功能强大的第三方库,实现在Word文档中自动化创建图表,为你的数据呈现和报告生成提供一套实用且高效的解决方... 目录Word文档图表自动化:为什么选择C#?从零开始:C#实现Word文档图表的基本步骤深度优化:C

在C#中分离饼图的某个区域的操作指南

《在C#中分离饼图的某个区域的操作指南》在处理Excel饼图时,我们可能需要将饼图的各个部分分离出来,以使它们更加醒目,Spire.XLS提供了Series.DataFormat.Percent属性,... 目录引言如何设置饼图各分片之间分离宽度的代码示例:从整个饼图中分离单个分片的代码示例:引言在处理

C#借助Spire.XLS for .NET实现在Excel中添加文档属性

《C#借助Spire.XLSfor.NET实现在Excel中添加文档属性》在日常的数据处理和项目管理中,Excel文档扮演着举足轻重的角色,本文将深入探讨如何在C#中借助强大的第三方库Spire.... 目录为什么需要程序化添加Excel文档属性使用Spire.XLS for .NET库实现文档属性管理Sp

C++ move 的作用详解及陷阱最佳实践

《C++move的作用详解及陷阱最佳实践》文章详细介绍了C++中的`std::move`函数的作用,包括为什么需要它、它的本质、典型使用场景、以及一些常见陷阱和最佳实践,感兴趣的朋友跟随小编一起看... 目录C++ move 的作用详解一、一句话总结二、为什么需要 move?C++98/03 的痛点⚡C++

MySQL快速复制一张表的四种核心方法(包括表结构和数据)

《MySQL快速复制一张表的四种核心方法(包括表结构和数据)》本文详细介绍了四种复制MySQL表(结构+数据)的方法,并对每种方法进行了对比分析,适用于不同场景和数据量的复制需求,特别是针对超大表(1... 目录一、mysql 复制表(结构+数据)的 4 种核心方法(面试结构化回答)方法 1:CREATE