自动编码

master
smartwyy 6 months ago
parent 9d3ac3270c
commit a125e541de

@ -1,44 +1,183 @@
// See https://aka.ms/new-console-template for more information
using System.Reflection;
using System.Text;
using ConsoleStarter;
using System.Collections;
using HybirdFrameworkCore.Autofac.Attribute;
using HybirdFrameworkCore.Utils;
internal class Program
{
public static void Main(string[] args)
{
List<PropertyAttribute> list = new List<PropertyAttribute>
{
new(0, 4),
new(4, 8),
new(12, 1),
new(13, 2),
new(15, 1),
new(16, 1),
new(17, 1),
new(18, 2),
new(20, 2),
new(22, 2),
new(24, 2),
new(26, 1),
new(27, 2),
new(29, 2),
new(31, 1),
new(32, 1),
new(33, 29)
};
int start = 0;
int length = 0;
foreach (PropertyAttribute attribute in list)
{
if (start < attribute.Start)
{
start = attribute.Start;
length = attribute.Length;
}
}
Console.WriteLine($"{start}, {length}");
byte[] bytes = new Byte[] { 0xFE, 0xFF };
ushort uInt16 = BitConverter.ToUInt16(bytes);
Console.WriteLine($"{uInt16}, {BitUtls.BytesToHexStr(bytes)}");
BitArray bitArray = new BitArray(16);
int index = 0;
foreach (var b in bytes)
{
for (int i = 0; i < 8; i++)
{
bool flag = (b & (1 << (index % 8))) > 0;
Console.WriteLine(flag);
bitArray[index++] = flag;
}
}
byte[] newbytes = new byte[2];
bitArray.CopyTo(newbytes, 0);
foreach (var b in newbytes)
{
Console.WriteLine(b);
}
ushort int16 = BitConverter.ToUInt16(newbytes);
Console.WriteLine($"{int16}, {BitUtls.BytesToHexStr(newbytes)}");
UInt64 max = UInt64.MaxValue / 8;
byte[] bytes1 = BitConverter.GetBytes(max);
Console.WriteLine($"{max}, {BitUtls.BytesToHexStr(bytes1)}");
foreach (var b in bytes1)
{
Console.WriteLine(b);
}
}
private static void Test1()
{
Console.WriteLine("Hello, World!");
List<PropertyAttribute> list = new List<PropertyAttribute>
{
new(0, 4),
new(4, 8),
new(12, 1),
new(13, 2),
new(15, 1),
new(16, 1),
new(17, 1),
new(18, 2),
new(20, 2),
new(22, 2),
new(24, 2),
new(26, 1),
new(27, 2),
new(29, 2),
new(31, 1),
new(32, 1),
new(33, 29)
};
Type type = typeof(TestPerson);
var o = Activator.CreateInstance(type);
if (o != null)
Queue<EncodeData> queue = new Queue<EncodeData>();
int size = 0;
foreach (PropertyAttribute p in list)
{
size += p.Length;
if (size < 8)
{
queue.Enqueue(new EncodeData()
{
Start = 0, Length = p.Length
});
}
else
{
TestPerson person = (TestPerson) o;
foreach (PropertyInfo property in person.GetType().GetProperties())
Console.WriteLine("---------------------------begin one byte---------------------");
int length = 0;
while (queue.Count > 0)
{
Console.WriteLine(property.PropertyType);
EncodeData data = queue.Dequeue();
length += data.Length;
Console.WriteLine($"use {data.Start}, {data.Length}");
}
size -= length;
int occupy = 8 - length;
Console.WriteLine($"use 0, {occupy}");
Console.WriteLine("---------------------------end one byte---------------------");
size -= occupy;
while (size >= 8)
{
Console.WriteLine("---------------------------begin one byte---------------------");
Console.WriteLine($"use {occupy}, 8");
Console.WriteLine("---------------------------end one byte---------------------");
size -= 8;
occupy += 8;
}
UInt16 ui = 12;
Console.WriteLine(Convert.ToInt16(ui));
Console.WriteLine(BitConverter.IsLittleEndian);
if (size > 0)
{
queue.Enqueue(new EncodeData()
{
Start = occupy, Length = size
});
}
}
}
foreach (EncodeData d in queue)
{
Console.WriteLine($"{d.Start}, {d.Length}");
}
string str = "€";
//1252 windows-1252 ANSI Latin 1; Western European (Windows)
var array = Encoding.Unicode.GetBytes(str);
foreach (byte b in array)
UInt32 i = UInt32.MaxValue - 1;
byte[] bytes = BitConverter.GetBytes(i).Reverse().ToArray();
foreach (byte b in bytes)
{
Console.WriteLine(b);
}
Console.WriteLine(BitUtls.BytesToHexStr(array));
var array2 = Encoding.BigEndianUnicode.GetBytes(str);
Console.WriteLine(BitUtls.BytesToHexStr(array2));
Console.WriteLine(BitUtls.BytesToHexStr(bytes));
UInt32 r = BitConverter.ToUInt32(bytes);
Console.WriteLine(r);
bytes = BitConverter.GetBytes(r);
foreach (byte b in bytes)
{
Console.WriteLine(b);
}
Console.WriteLine(BitUtls.BytesToHexStr(bytes));
}
}
public struct EncodeData
{
public int Start { get; set; }
public int Length { get; set; }
public byte[] Value { get; set; }
}

@ -1,4 +1,6 @@
using System.Reflection;
using System.Collections;
using System.Reflection;
using System.Text;
using HybirdFrameworkCore.Autofac.Attribute;
namespace HybirdFrameworkCore.Utils;
@ -18,7 +20,7 @@ public static class ModelConvert
private static readonly Type DOUBLE = typeof(double);
private static readonly Type STRING = typeof(string);
public static T Decode<T>(byte[] bytes) where T : class, new()
public static T Declode<T>(byte[] bytes) where T : class, new()
{
T t = new T();
@ -94,27 +96,105 @@ public static class ModelConvert
public static byte[] Encode<T>(T t) where T : class, new()
{
List<byte> list = new List<byte>();
Type type = t.GetType();
PropertyInfo[] fields = type.GetProperties();
Dictionary<PropertyAttribute, PropertyInfo> dictionary = new Dictionary<PropertyAttribute, PropertyInfo>();
int start = 0;
int length = 0;
foreach (var field in fields)
{
PropertyAttribute? attribute = field.GetCustomAttribute<PropertyAttribute>();
if (attribute != null)
{
if (start <= attribute.Start)
{
start = attribute.Start;
length = attribute.Length;
}
dictionary.Add(attribute, field);
}
}
int maxLength = start + length;
BitArray bitArray = new BitArray(maxLength);
byte[] result = new Byte[maxLength % 8 == 0 ? maxLength / 8 : maxLength / 8 + 1];
PropertyAttribute[] attributes = dictionary.Keys.ToArray();
Array.Sort(attributes, (a, b) => a.Start.CompareTo(b.Start));
return list.ToArray();
foreach (PropertyAttribute attribute in attributes)
{
PropertyInfo field = dictionary[attribute];
byte[] value = GetPropertyValue(t, field, attribute);
start = attribute.Start;
length = attribute.Length;
for (int i = 0; i < length; i++)
{
bitArray[start + i] = (value[i % 8] & (1 << i % 8)) > 0;
}
}
bitArray.CopyTo(result, 0);
return result;
}
private static byte[] GetPropertyValue<T>(T t, PropertyInfo field, PropertyAttribute attribute)
{
double offset = attribute.Offset;
double scale = attribute.Scale;
Type propertyType = field.PropertyType;
object? value = field.GetValue(t);
if (value == null)
{
return Array.Empty<byte>();
}
if (propertyType == BOOLEAN)
{
return BitConverter.GetBytes((bool)value);
}
if (propertyType == BYTE || propertyType == SBYTE)
{
return new[] { (byte)(((byte)value + offset) / scale) };
}
if (propertyType == USHORT)
{
return BitConverter.GetBytes((ushort)(((short)value + offset) / scale));
}
if (propertyType == SHORT)
{
return BitConverter.GetBytes((short)(((short)value + offset) / scale));
}
if (propertyType == INT)
{
return BitConverter.GetBytes((int)(((int)value + offset) / scale));
}
if (propertyType == UINT)
{
return BitConverter.GetBytes((uint)(((uint)value + offset) / scale));
}
if (propertyType == FLOAT)
{
return BitConverter.GetBytes((uint)(((float)value + offset) / scale));
}
private static byte[] GetPropertyValue()
if (propertyType == DOUBLE)
{
return new byte[]{0};
return BitConverter.GetBytes((UInt64)(((double)value + offset) / scale));
}
if (propertyType == STRING)
{
return Encoding.ASCII.GetBytes((string)value);
}
throw new ArgumentException($"参数类型{propertyType}不支持encode");
}
}
Loading…
Cancel
Save