C#中把一个Struct结构转换成Byte[]的方法
2021/9/17 9:04:54
本文主要是介绍C#中把一个Struct结构转换成Byte[]的方法,对大家解决编程问题具有一定的参考价值,需要的程序猿们随着小编来一起学习吧!
哈喽,好久没写了。
今天分享一个标准库
在C#中把一个struct转换成byte[]输出的方法
直接上代码
public static byte[] StructToBytes(object structObj) { //返回类的非托管大小(以字节为单位) int size = Marshal.SizeOf(structObj); //分配大小 byte[] bytes = new byte[size]; //从进程的非托管堆中分配内存给structPtr IntPtr structPtr = Marshal.AllocHGlobal(size); try { //将数据从托管对象structObj封送到非托管内存块structPtr Marshal.StructureToPtr(structObj, structPtr, false); //Marshal.StructureToPtr(structObj, structPtr, true); //将数据从非托管内存指针复制到托管 8 位无符号整数数组 Marshal.Copy(structPtr, bytes, 0, size); return bytes; } catch (Exception ex) { return null; } finally { //释放以前使用 AllocHGlobal 从进程的非托管内存中分配的内存 Marshal.FreeHGlobal(structPtr); } }
这里使用到了非托管内存,就是自己控制资源开启和释放的区域。
下面在分享一个StructToByte的Helper:
public class ByteHelper { /// <summary> /// 获取取第index位 /// </summary> /// <param name="b"></param> /// <param name="index"></param> /// <returns></returns> public static int GetBit(byte b, int index) { return ((b & (1 << index)) > 0) ? 1 : 0; } /// <summary> /// 将第index位设为1 /// </summary> /// <param name="b"></param> /// <param name="index"></param> /// <returns></returns> public static byte SetBit(byte b, int index) { return (byte)(b | (1 << index)); } /// <summary> /// 将第index位设为0 /// </summary> /// <param name="b"></param> /// <param name="index"></param> /// <returns></returns> public static byte ClearBit(byte b, int index) { return (byte)(b & (byte.MaxValue - (1 << index))); } /// <summary> /// 将第index位取反 /// </summary> /// <param name="b"></param> /// <param name="index"></param> /// <returns></returns> public static byte ReverseBit(byte b, int index) { return (byte)(b ^ (byte)(1 << index)); } /// <summary> /// 将字节A写入目标字节B的指定位 /// </summary> /// <param name="Value">字节B 超过8位时低位数组索引小于高位</param> /// <param name="Index">起始位置</param> /// <param name="Leng">占位长度</param> /// <param name="OriginalValue">A字节</param> /// <returns></returns> public static byte[] BitProcessing(byte[] Value, int Index, int Leng, byte OriginalValue) { bool Med; for (int index = 1; index <= Leng; index++) { byte Weight = (byte)Math.Pow(2, index - 1); Med = ((OriginalValue & Weight) == Weight); int Cursor = Index + index - 1; Value[Cursor / 8] = set_bit(Value[Cursor / 8], Cursor % 8, Med); } return Value; } /// <summary> /// 设置字节任意位 /// </summary> /// <param name="data"></param> /// <param name="index"></param> /// <param name="flag"></param> /// <returns></returns> private static byte set_bit(byte data, int index, bool flag) { ++index; if (index > 8 || index < 1) throw new ArgumentOutOfRangeException(); int v = index < 2 ? index : (2 << (index - 2)); return flag ? (byte)(data | v) : (byte)(data & ~v); } public static byte[] StructToBytes(object structObj) { //返回类的非托管大小(以字节为单位) int size = Marshal.SizeOf(structObj); //分配大小 byte[] bytes = new byte[size]; //从进程的非托管堆中分配内存给structPtr IntPtr structPtr = Marshal.AllocHGlobal(size); try { //将数据从托管对象structObj封送到非托管内存块structPtr Marshal.StructureToPtr(structObj, structPtr, false); //Marshal.StructureToPtr(structObj, structPtr, true); //将数据从非托管内存指针复制到托管 8 位无符号整数数组 Marshal.Copy(structPtr, bytes, 0, size); return bytes; } catch (Exception ex) { return null; } finally { //释放以前使用 AllocHGlobal 从进程的非托管内存中分配的内存 Marshal.FreeHGlobal(structPtr); } } public static object BytesToStruct(byte[] bytes, Type strType) { //获取结构体的大小(以字节为单位) int size = Marshal.SizeOf(strType); //简单的判断(可以去掉) if (size > bytes.Length) { return null; } //从进程的非托管堆中分配内存给structPtr IntPtr strPtr = Marshal.AllocHGlobal(size); try { //将数据从一维托管数组bytes复制到非托管内存指针strPtr Marshal.Copy(bytes, 0, strPtr, size); //将数据从非托管内存块封送到新分配的指定类型的托管对象 //将内存空间转换为目标结构体 object obj = Marshal.PtrToStructure(strPtr, strType); return obj; } catch (Exception ex) { return null; } finally { //释放以前使用 AllocHGlobal 从进程的非托管内存中分配的内存 Marshal.FreeHGlobal(strPtr); } } }ByteHelper
最后顺带说一下,一般看到了我这个文章的都是对Struct进行转换了。别忘记内存对其方式哦
[StructLayout(LayoutKind.Sequential)]
贴在你的Struct类上面,
[StructLayout(LayoutKind.Sequential, Pack = 1)]
pack=1表示标准对其
需要带走
这篇关于C#中把一个Struct结构转换成Byte[]的方法的文章就介绍到这儿,希望我们推荐的文章对大家有所帮助,也希望大家多多支持为之网!
- 2022-03-01沐雪多租宝商城源码从.NetCore3.1升级到.Net6的步骤
- 2024-12-06使用Microsoft.Extensions.AI在.NET中生成嵌入向量
- 2024-11-18微软研究:RAG系统的四个层次提升理解与回答能力
- 2024-11-15C#中怎么从PEM格式的证书中提取公钥?-icode9专业技术文章分享
- 2024-11-14云架构设计——如何用diagrams.net绘制专业的AWS架构图?
- 2024-05-08首个适配Visual Studio平台的国产智能编程助手CodeGeeX正式上线!C#程序员必备效率神器!
- 2024-03-30C#设计模式之十六迭代器模式(Iterator Pattern)【行为型】
- 2024-03-29c# datetime tryparse
- 2024-02-21list find index c#
- 2024-01-24convert toint32 c#