Windows Phone 7 网络字节序列化(结构转字节)实现

2023-11-03

令人激动的Windows Phone 7 Mango(WP7)版本开放了Socket接口,虽有些Socket功能无法实现令人遗憾,但还是进步了一些。

有了Socket我们就可以用其为我们传递Byte[]数据流,而我们的数据又经常保存在struct或者class中,但是WP7对这种结构到字节的支持欠佳(或许我没有发现,.net完整版中使用的全局内存分配方式在WP7不被允许),所以有了如下代码,它将为你的WP7网络开发尽一份微薄之力。

编码仓促,若有错误,还请反馈,共同完善

 

// 测试代码
 
public class Person
{
    public int age;
    public string str;
    public byte[] data;
}
 
Person scott = new Person();
scott.age = 50;
scott.str = "nothing";
scott.data = new byte[] { 12, 13, 15, 16, 17 };
byte[] result = Fyter.Utility.StructSerializer.StructToBytes(scott);
 
Person other = new Person();
Fyter.Utility.StructSerializer.BytesToStruct(result, other);

 

 

// 源代码文件 : StructSerializer.cs

 

using System;
using System.Reflection;
using System.Collections.Generic;
using System.Linq;
 
namespace Fyter.Utility
{
    /// <summary>
    /// 结构序列化工具
    /// 可以将结构、类转换为字节流,支持Windows Phone 7
    /// 仅使用静态成员函数即可,按提示操作
    /// 转换过程请截获异常
    /// </summary>
    public class StructSerializer
    {
        class pair
        {
            public bool isarray;
            public byte[] data;
            public pair(bool v, byte[] p)
            {
                isarray = v;
                data = p;
            }
        }
 
        //delegate pair GetBytes(FieldInfo fi, object o);// 也可以使用委托
 
        static Dictionary<TypeFunc<FieldInfoobject, pair>> tg =
            new Dictionary<TypeFunc<FieldInfoobject, pair>>{
            {typeof(Int16), GetInt16Bytes},
            {typeof(Int32), GetInt32Bytes},
            {typeof(Int64), GetInt64Bytes},
            {typeof(UInt16), GetUInt16Bytes},
            {typeof(UInt32), GetUInt32Bytes},
            {typeof(UInt64), GetUInt64Bytes},
            {typeof(char), GetCharBytes},
            {typeof(byte), GetInt8Bytes},
            {typeof(byte[]), GetByteArrayBytes},
            {typeof(string), GetStringBytes}
            };
 
        static Dictionary<TypeFunc<FieldInfoobjectbyte[], intint>> ts =
            new Dictionary<TypeFunc<FieldInfoobjectbyte[], intint>>{
            {typeof(Int16), SetInt16Bytes},
            {typeof(Int32), SetInt32Bytes},
            {typeof(Int64), SetInt64Bytes},
            {typeof(UInt16), SetUInt16Bytes},
            {typeof(UInt32), SetUInt32Bytes},
            {typeof(UInt64), SetUInt64Bytes},
            {typeof(char), SetCharBytes},
            {typeof(byte), SetInt8Bytes},
            {typeof(byte[]), SetByteArrayBytes},
            {typeof(string), SetStringBytes}
            };
 
 
 
        static pair GetInt8Bytes(FieldInfo fi, object o)
        {
            return new pair(falsenew byte[1]{(byte)fi.GetValue(o)});
        }
 
        static int SetInt8Bytes(FieldInfo fi, object o, byte[] data, int offset)
        {
            fi.SetValue(o, data[offset]);
            return sizeof(byte);
        }
 
        static pair GetCharBytes(FieldInfo fi, object o)
        {
            return new pair(falseBitConverter.GetBytes((Char)fi.GetValue(o)));
        }
 
        static int SetCharBytes(FieldInfo fi, object o, byte[] data, int offset)
        {
            fi.SetValue(o, BitConverter.ToChar(data, offset));
            return sizeof(char);
        }
 
        static pair GetInt16Bytes(FieldInfo fi, object o)
        {
            return new pair(falseBitConverter.GetBytes((Int16)fi.GetValue(o)));
        }
 
        static int SetInt16Bytes(FieldInfo fi, object o, byte[] data, int offset)
        {
            fi.SetValue(o, BitConverter.ToInt16(data, offset));
            return sizeof(Int16);
        }
 
        static pair GetInt32Bytes(FieldInfo fi, object o)
        {
            return new pair(falseBitConverter.GetBytes((Int32)fi.GetValue(o)));
        }
 
        static int SetInt32Bytes(FieldInfo fi, object o, byte[] data, int offset)
        {
            fi.SetValue(o, BitConverter.ToInt32(data, offset));
            return sizeof(Int32);
        }
 
        static pair GetInt64Bytes(FieldInfo fi, object o)
        {
            return new pair(falseBitConverter.GetBytes((Int64)fi.GetValue(o)));
        }
 
        static int SetInt64Bytes(FieldInfo fi, object o, byte[] data, int offset)
        {
            fi.SetValue(o, BitConverter.ToInt64(data, offset));
            return sizeof(Int64);
        }
 
        static pair GetUInt16Bytes(FieldInfo fi, object o)
        {
            return new pair(falseBitConverter.GetBytes((UInt16)fi.GetValue(o)));
        }
 
        static int SetUInt16Bytes(FieldInfo fi, object o, byte[] data, int offset)
        {
            fi.SetValue(o, BitConverter.ToUInt16(data, offset));
            return sizeof(UInt16);
        }
 
        static pair GetUInt32Bytes(FieldInfo fi, object o)
        {
            return new pair(falseBitConverter.GetBytes((UInt32)fi.GetValue(o)));
        }
 
        static int SetUInt32Bytes(FieldInfo fi, object o, byte[] data, int offset)
        {
            fi.SetValue(o, BitConverter.ToUInt32(data, offset));
            return sizeof(UInt32);
        }
 
        static pair GetUInt64Bytes(FieldInfo fi, object o)
        {
            return new pair(falseBitConverter.GetBytes((UInt64)fi.GetValue(o)));
        }
 
        static int SetUInt64Bytes(FieldInfo fi, object o, byte[] data, int offset)
        {
            fi.SetValue(o, BitConverter.ToUInt64(data, offset));
            return sizeof(UInt64);
        }
 
        static pair GetByteArrayBytes(FieldInfo fi, object o)
        {
            return new pair(true, (byte[])fi.GetValue(o));
        }
 
        static int SetByteArrayBytes(FieldInfo fi, object o, byte[] data, int offset)
        {
            UInt16 len = BitConverter.ToUInt16(data, offset);
            byte[] result = new byte[len];
            Array.Copy(data, offset + 2, result, 0, len);
            fi.SetValue(o, result);
            return sizeof(Int16) + len;
        }
 
        static pair GetStringBytes(FieldInfo fi, object o)
        {
            return new pair(true, System.Text.UnicodeEncoding.Unicode.GetBytes((string)fi.GetValue(o)));
        }
 
        static int SetStringBytes(FieldInfo fi, object o, byte[] data, int offset)
        {
            UInt16 len = BitConverter.ToUInt16(data, offset);
            fi.SetValue(o, System.Text.UnicodeEncoding.Unicode.GetString(data, offset+2, len));
            return sizeof(UInt16) + len;
        }
 
        /// <summary>
        /// 结构实例转换为字节流
        /// obj最大支持65535个字符的字符串或字节流成员变量,请自行校验
        /// </summary>
        /// <param name="obj">预转换的对象</param>
        /// <returns>字节流</returns>
        static public Byte[] StructToBytes(Object obj)
        {
            List<pair> hs = new List<pair>();
            int count = 0;
 
            foreach (FieldInfo fi in obj.GetType().GetFields(BindingFlags.Public | BindingFlags.Instance))
            {
                if (ts.Keys.Contains(fi.FieldType))
                {
                    pair temp = tg[fi.FieldType](fi, obj);
                    if (temp.isarray)
                    {
                        count += 2;
                    }
                    count += temp.data.Length;
                    hs.Add(temp);
                }
            }
 
            byte[] result = new byte[count];
            int offset = 0;
 
            foreach (pair pr in hs)
            {
                if (pr.isarray)
                {
                    BitConverter.GetBytes((ushort)pr.data.Length).CopyTo(result, offset);
                    offset += 2;
                }
                pr.data.CopyTo(result, offset);
                offset += pr.data.Length;
            }
 
            return result;
        }
 
        /// <summary>
        /// 字节流传递到目标对象
        /// </summary>
        /// <param name="src">源数据流</param>
        /// <param name="obj">预转换的对象</param>
        static public void BytesToStruct(Byte[] src, Object obj)
        {
            int offset = 0;
 
            foreach (FieldInfo fi in obj.GetType().GetFields(BindingFlags.Public | BindingFlags.Instance))
            {
                if (ts.Keys.Contains(fi.FieldType))
                {
                    offset += ts[fi.FieldType](fi, obj, src, offset);
                }
            }
        }
    }
}

 

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

Windows Phone 7 网络字节序列化(结构转字节)实现 的相关文章

随机推荐

  • git、KDiff3、Git Extensions

    Git git概念 Git 是一个开源的分布式版本控制系统 用于敏捷高效地处理任何或小或大的项目 1 下载git软件路径 https git scm com download win 2 点击安装 一直下一步直到finish git下载后的
  • 为什么sql里面not in后面的子查询如果有记录为NULL的,主查询就查不到记录

    为什么sql里面not in后面的子查询如果有记录为NULL的 主查询就查不到记录 原因很简单 SELECT FROM dbo TableA AS a WHERE a id NOT IN 2 NULL 等同于 SELECT FROM Tab
  • SSM概述

    SSM概述 基本概念 SSM Spring SpringMVC MyBatis Spring 简单来说 就是一个轻量级的控制反转 IOC 和面向切面 AOP 的容器框架 其中IOC可以说是SSM的核心之一 SpringMVC 分离了控制器
  • 技术至简-5:动画显示复指数信号的形状与物理意义

    复指数信号概念的理解是一个难点 1 数学表达式 它是由两个同频的正弦和余弦两个基本信号构成 2 复指数信号的内在组成 复指数是两路正交的基本信号 一路是余弦信号 另一路是正弦信号 3 复指数的物理含义 那么含有两路两路正交的基本信号的虚指数
  • 数组JAVA

    JAVA数组详情 什么是数组 数组就是 存储一组数据类型相同的数据元素 数组在内存中空间是连续的 长度初始好 就不能再做改变 数组是属于应用类型的 对象 所以也就可以即存储基本数据类型 还可以存储引用类型 数组的声明 int a 这是声明了
  • cba篮球暂停次数和时间_CBA一场比赛每支球队可以叫多少次暂停

    展开全部 CBA一场比赛在48分钟内两个队最多会有18次暂停 两个官方暂停 62616964757a686964616fe78988e69d833133343364643512个常规暂停 4个短暂停 每个加时赛每个队有三次60秒常规暂停 4
  • Simulink如何添加模块到Library Browser

    文章目录 一 新建Library 1 创建空的Library模块 2 编辑Library 二 添加到Library Browser 1 添加Library的脚本命令 2 新建脚本文件 3 导入Library模块 提示 以下是本篇文章正文内容
  • 华为OD机试 Java 实现【求int型正整数在内存中存储时1的个数】【牛客练习题 HJ15】,附详细解题思路

    一 题目描述 输入一个 int 型的正整数 计算出该 int 型数据在内存中存储时 1 的个数 数据范围 保证在 32 位整型数字范围内 二 输入描述 输入一个整数 int类型 三 输出描述 这个数转换成2进制后 输出1的个数 四 解题思路
  • flutter配置签名文件

    前言 flutter要调用手机的一些功能时会使用到手机模拟器 手机模拟器就需要配置apk了 实现步骤 第一步 生成我们需要的key 在你要生成文件的地方打开 terminal 小黑框执行下列命令 keytool genkey v keyst
  • 赛桨启航!飞桨助力2023年“大湾区杯”粤港澳AI4S竞赛

    近年来 人工智能技术日新月异 创新成果赋能生物医学 材料 金融 气象等千行百业 人工智能技术引领的新一轮科技革命和产业变革浪潮 将成为未来世界经济和高端制造的主导技术 更会对中国现代化产业体系建设发挥无可替代的作用 立足新时代 百度飞桨携广
  • 安装Redis教程(详细过程)

    提示 文章写完后 目录可以自动生成 如何生成可参考右边的帮助文档 文章目录 一 Redis是什么 二 安装步骤 一 Redis是什么 Redis是一个开源内存数据结构存储器 经常用做数据库 缓存以及消息代理等 Redis因其丰富的数据结构
  • java开发外包是什么意思,一文全懂

    个人基本情况 首先介绍一下自己的个人基本情况 某专科学校毕业 计算机技术与应用专业 有过2年的工作经验 毕业以后一直想要进入一线互联网大厂工作 但无奈学历受限 屡屡被挡在门外 后来接触到一个朋友 了解到 霸面 所以鼓起勇气去尝试了 挑战了一
  • Python uWSGI 安装配置

    目录 前言 Python 安装 uWSGI 第一个 WSGI 应用 添加并发和监控 结合 Web 服务器使用 部署 Django 部署 Flask 前言 本文主要介绍如何部署简单的 WSGI 应用和常见的 Web 框架 以 Ubuntu D
  • MLS multilayer switch

    一次路由 多次交换 pps packets per second bps bits per second Bps byte per second Mpps millions of pps 如果交换机启用了MLS特性 那么交换机将会记录发往路
  • go语言的常见函数

    1 make函数 创建数组切片 Go语言提供的内置函数make 可以用于灵活地创建数组切片 创建一个初始元素个数为5的数组切片 元素初始值为0 mySlice1 make int 5 创建一个初始元素个数为5的数组切片 元素初始值为0 并预
  • 组件化2---APT的实现(ARoute)--传统写法和JavaPoet写法

    APT技术就是得用注解来自动生成一些类式代码 比如下面这个注解 Target ElementType TYPE Retention RetentionPolicy CLASS public interface ARouter String
  • Matlab图像操作——colorbar的详细使用方法与细节操作

    Matlab图像操作 colorbar的详细使用方法与细节操作 在Matlab中 colorbar是一种常用的工具 用于显示图像的颜色条 它提供了对图像色彩的可视化表示 使得用户能够更直观地理解图像数据的分布和范围 本文将介绍colorba
  • 网络传输一丢丢记录【数据包大小限制】

    今早用udp传一个对象序列化字节数组 大小达到了7000 字节 然后udp的send就报异常 一个在数据报套接字上发送的消息大于内部消息缓冲区或其他一些网络限制 或该用户用于接收数据报的缓冲区比数据报小 网上查了一下 说是超过udp的单包容
  • vue获取当前位置的信息以及天气信息

    1 首先在https lbs qq com 这个网页中 先使用微信 注册一个 1 1然后创建应用 1 2创建你的key 效果如下 这里面必须填写 0 0 0 0 255 255 25 255 2 使用npm下载jsonp插件 命令 npm
  • Windows Phone 7 网络字节序列化(结构转字节)实现

    令人激动的Windows Phone 7 Mango WP7 版本开放了Socket接口 虽有些Socket功能无法实现令人遗憾 但还是进步了一些 有了Socket我们就可以用其为我们传递Byte 数据流 而我们的数据又经常保存在struc