diff --git a/Modbus.Net/Modbus.Net.Modbus/Modbus.Net.Modbus.nuspec b/Modbus.Net/Modbus.Net.Modbus/Modbus.Net.Modbus.nuspec index c070fd2..4abb43c 100644 --- a/Modbus.Net/Modbus.Net.Modbus/Modbus.Net.Modbus.nuspec +++ b/Modbus.Net/Modbus.Net.Modbus/Modbus.Net.Modbus.nuspec @@ -2,7 +2,7 @@ Modbus.Net.Modbus - 1.2.3 + 1.2.3.2 Modbus.Net.Modbus Chris L.(Luo Sheng) Hangzhou Delian IoT Science Technology Co.,Ltd. @@ -13,7 +13,7 @@ Copyright 2017 Hangzhou Delian IoT Science Technology Co.,Ltd. hardware communicate protocal modbus Delian - + diff --git a/Modbus.Net/Modbus.Net.Modbus/ModbusMachine.cs b/Modbus.Net/Modbus.Net.Modbus/ModbusMachine.cs index 72f252d..c209bb9 100644 --- a/Modbus.Net/Modbus.Net.Modbus/ModbusMachine.cs +++ b/Modbus.Net/Modbus.Net.Modbus/ModbusMachine.cs @@ -1,26 +1,50 @@ -using System.Collections.Generic; +using System; +using System.Collections.Generic; namespace Modbus.Net.Modbus { /// /// Modbus设备 /// - public class ModbusMachine : BaseMachine + public class ModbusMachine : BaseMachine where TKey : IEquatable + where TUnitKey : IEquatable { public ModbusMachine(ModbusType connectionType, string connectionString, - IEnumerable getAddresses, bool keepConnect, byte slaveAddress, byte masterAddress, Endian endian = Endian.BigEndianLsb) + IEnumerable> getAddresses, bool keepConnect, byte slaveAddress, byte masterAddress, + Endian endian = Endian.BigEndianLsb) : base(getAddresses, keepConnect, slaveAddress, masterAddress) { BaseUtility = new ModbusUtility(connectionType, connectionString, slaveAddress, masterAddress, endian); AddressFormater = new AddressFormaterModbus(); - AddressCombiner = new AddressCombinerContinus(AddressTranslator); - AddressCombinerSet = new AddressCombinerContinus(AddressTranslator); + AddressCombiner = new AddressCombinerContinus(AddressTranslator); + AddressCombinerSet = new AddressCombinerContinus(AddressTranslator); } public ModbusMachine(ModbusType connectionType, string connectionString, - IEnumerable getAddresses, byte slaveAddress, byte masterAddress, Endian endian = Endian.BigEndianLsb) + IEnumerable> getAddresses, byte slaveAddress, byte masterAddress, + Endian endian = Endian.BigEndianLsb) : this(connectionType, connectionString, getAddresses, false, slaveAddress, masterAddress, endian) { } } + + /// + /// Modbus设备 + /// + public class ModbusMachine : ModbusMachine + { + public ModbusMachine(ModbusType connectionType, string connectionString, + IEnumerable> getAddresses, + bool keepConnect, byte slaveAddress, byte masterAddress, Endian endian = Endian.BigEndianLsb) + : base(connectionType, connectionString, getAddresses, keepConnect, slaveAddress, masterAddress, endian) + { + } + + public ModbusMachine(ModbusType connectionType, string connectionString, + IEnumerable> getAddresses, + byte slaveAddress, byte masterAddress, Endian endian = Endian.BigEndianLsb) + : base(connectionType, connectionString, getAddresses, slaveAddress, masterAddress, endian) + { + } + } } \ No newline at end of file diff --git a/Modbus.Net/Modbus.Net.OPC/Modbus.Net.OPC.nuspec b/Modbus.Net/Modbus.Net.OPC/Modbus.Net.OPC.nuspec index c6aa811..73dfd19 100644 --- a/Modbus.Net/Modbus.Net.OPC/Modbus.Net.OPC.nuspec +++ b/Modbus.Net/Modbus.Net.OPC/Modbus.Net.OPC.nuspec @@ -13,7 +13,7 @@ Copyright 2017 Hangzhou Delian IoT Science Technology Co.,Ltd. hardware communicate protocal OPC DA Delian - + diff --git a/Modbus.Net/Modbus.Net.OPC/OpcDaMachine.cs b/Modbus.Net/Modbus.Net.OPC/OpcDaMachine.cs index 6f072ce..e30c17f 100644 --- a/Modbus.Net/Modbus.Net.OPC/OpcDaMachine.cs +++ b/Modbus.Net/Modbus.Net.OPC/OpcDaMachine.cs @@ -1,23 +1,41 @@ -using System.Collections.Generic; +using System; +using System.Collections.Generic; namespace Modbus.Net.OPC { /// /// OpcDa设备 /// - public class OpcDaMachine : BaseMachine + public class OpcDaMachine : BaseMachine where TKey : IEquatable + where TUnitKey : IEquatable { - public OpcDaMachine(string connectionString, IEnumerable getAddresses, bool keepConnect) + public OpcDaMachine(string connectionString, IEnumerable> getAddresses, bool keepConnect) : base(getAddresses, keepConnect) { BaseUtility = new OpcDaUtility(connectionString); - AddressCombiner = new AddressCombinerSingle(); - AddressCombinerSet = new AddressCombinerSingle(); + AddressCombiner = new AddressCombinerSingle(); + AddressCombinerSet = new AddressCombinerSingle(); } - public OpcDaMachine(string connectionString, IEnumerable getAddresses) + public OpcDaMachine(string connectionString, IEnumerable> getAddresses) : this(connectionString, getAddresses, false) { } } + + /// + /// OpcDa设备 + /// + public class OpcDaMachine : OpcDaMachine + { + public OpcDaMachine(string connectionString, IEnumerable> getAddresses, bool keepConnect) + : base(connectionString, getAddresses, keepConnect) + { + } + + public OpcDaMachine(string connectionString, IEnumerable> getAddresses) + : base(connectionString, getAddresses) + { + } + } } \ No newline at end of file diff --git a/Modbus.Net/Modbus.Net.Siemens/Modbus.Net.Siemens.nuspec b/Modbus.Net/Modbus.Net.Siemens/Modbus.Net.Siemens.nuspec index 49d8a46..82af50d 100644 --- a/Modbus.Net/Modbus.Net.Siemens/Modbus.Net.Siemens.nuspec +++ b/Modbus.Net/Modbus.Net.Siemens/Modbus.Net.Siemens.nuspec @@ -13,7 +13,7 @@ Copyright 2017 Hangzhou Delian IoT Science Technology Co.,Ltd. hardware communicate protocal Siemens profinet Delian - + diff --git a/Modbus.Net/Modbus.Net.Siemens/SiemensMachine.cs b/Modbus.Net/Modbus.Net.Siemens/SiemensMachine.cs index 6eac8d6..eca454a 100644 --- a/Modbus.Net/Modbus.Net.Siemens/SiemensMachine.cs +++ b/Modbus.Net/Modbus.Net.Siemens/SiemensMachine.cs @@ -1,26 +1,46 @@ -using System.Collections.Generic; +using System; +using System.Collections.Generic; namespace Modbus.Net.Siemens { /// /// 西门子设备 /// - public class SiemensMachine : BaseMachine + public class SiemensMachine : BaseMachine where TKey : IEquatable + where TUnitKey : IEquatable { public SiemensMachine(SiemensType connectionType, string connectionString, SiemensMachineModel model, - IEnumerable getAddresses, bool keepConnect, byte slaveAddress, byte masterAddress) + IEnumerable> getAddresses, bool keepConnect, byte slaveAddress, byte masterAddress) : base(getAddresses, keepConnect, slaveAddress, masterAddress) { BaseUtility = new SiemensUtility(connectionType, connectionString, model, slaveAddress, masterAddress); AddressFormater = new AddressFormaterSiemens(); - AddressCombiner = new AddressCombinerContinus(AddressTranslator); - AddressCombinerSet = new AddressCombinerContinus(AddressTranslator); + AddressCombiner = new AddressCombinerContinus(AddressTranslator); + AddressCombinerSet = new AddressCombinerContinus(AddressTranslator); } public SiemensMachine(SiemensType connectionType, string connectionString, SiemensMachineModel model, - IEnumerable getAddresses, byte slaveAddress, byte masterAddress) + IEnumerable> getAddresses, byte slaveAddress, byte masterAddress) : this(connectionType, connectionString, model, getAddresses, false, slaveAddress, masterAddress) { } } + + /// + /// 西门子设备 + /// + public class SiemensMachine : SiemensMachine + { + public SiemensMachine(SiemensType connectionType, string connectionString, SiemensMachineModel model, + IEnumerable> getAddresses, bool keepConnect, byte slaveAddress, byte masterAddress) + : base(connectionType, connectionString, model, getAddresses, keepConnect, slaveAddress, masterAddress) + { + } + + public SiemensMachine(SiemensType connectionType, string connectionString, SiemensMachineModel model, + IEnumerable> getAddresses, byte slaveAddress, byte masterAddress) + : base(connectionType, connectionString, model, getAddresses, slaveAddress, masterAddress) + { + } + } } \ No newline at end of file diff --git a/Modbus.Net/Modbus.Net/AddressCombiner.cs b/Modbus.Net/Modbus.Net/AddressCombiner.cs index 90c53b6..3c7ef51 100644 --- a/Modbus.Net/Modbus.Net/AddressCombiner.cs +++ b/Modbus.Net/Modbus.Net/AddressCombiner.cs @@ -7,20 +7,37 @@ namespace Modbus.Net /// /// 地址组合器,组合后的每一组地址将只需一次向设备进行通讯 /// - public abstract class AddressCombiner + public abstract class AddressCombiner : AddressCombiner + { + } + + /// + /// 地址组合器,组合后的每一组地址将只需一次向设备进行通讯 + /// + public abstract class AddressCombiner where TKey : IEquatable { /// /// 组合地址 /// /// 需要进行组合的地址 /// 组合完成后与设备通讯的地址 - public abstract IEnumerable Combine(IEnumerable addresses); + public abstract IEnumerable> Combine(IEnumerable> addresses); } /// /// 连续的地址将组合成一组,向设备进行通讯 /// - public class AddressCombinerContinus : AddressCombiner + public class AddressCombinerContinus : AddressCombinerContinus + { + public AddressCombinerContinus(AddressTranslator addressTranslator) : base(addressTranslator) + { + } + } + + /// + /// 连续的地址将组合成一组,向设备进行通讯 + /// + public class AddressCombinerContinus : AddressCombiner where TKey : IEquatable { public AddressCombinerContinus(AddressTranslator addressTranslator) { @@ -29,7 +46,7 @@ namespace Modbus.Net protected AddressTranslator AddressTranslator { get; set; } - public override IEnumerable Combine(IEnumerable addresses) + public override IEnumerable> Combine(IEnumerable> addresses) { //按从小到大的顺序对地址进行排序 var groupedAddresses = from address in addresses @@ -39,7 +56,7 @@ namespace Modbus.Net group address by address.Area into grouped select grouped; - var ans = new List(); + var ans = new List>(); foreach (var groupedAddress in groupedAddresses) { var area = groupedAddress.Key; @@ -50,7 +67,7 @@ namespace Modbus.Net //上一个地址类型 Type preType = null; //记录一个地址组合当中的所有原始地址 - var originalAddresses = new List(); + var originalAddresses = new List>(); //对组合内地址从小到大进行排序 var orderedAddresses = groupedAddress.OrderBy( @@ -97,7 +114,7 @@ namespace Modbus.Net AddressTranslator.GetAreaByteLength(address.Area))) { //上一个地址域压入返回结果,并把当前记录的结果清空。 - ans.Add(new CommunicationUnit + ans.Add(new CommunicationUnit { Area = area, Address = (int) Math.Floor(initNum), @@ -127,7 +144,7 @@ namespace Modbus.Net preType = address.DataType; } //最后一个地址域压入返回结果 - ans.Add(new CommunicationUnit + ans.Add(new CommunicationUnit { Area = area, Address = (int) Math.Floor(initNum), @@ -148,21 +165,28 @@ namespace Modbus.Net /// /// 单个地址变为一组,每一个地址都进行一次查询 /// - public class AddressCombinerSingle : AddressCombiner + public class AddressCombinerSingle : AddressCombinerSingle { - public override IEnumerable Combine(IEnumerable addresses) + } + + /// + /// 单个地址变为一组,每一个地址都进行一次查询 + /// + public class AddressCombinerSingle : AddressCombiner where TKey : IEquatable + { + public override IEnumerable> Combine(IEnumerable> addresses) { return addresses.Select( address => - new CommunicationUnit + new CommunicationUnit { Area = address.Area, Address = address.Address, SubAddress = address.SubAddress, DataType = address.DataType, GetCount = 1, - OriginalAddresses = new List {address} + OriginalAddresses = new List> {address} }).ToList(); } } @@ -170,16 +194,27 @@ namespace Modbus.Net /// /// 两个CommunicationUnit之间的间隔 /// - internal class CommunicationUnitGap + internal class CommunicationUnitGap where TKey : IEquatable { - public CommunicationUnit EndUnit { get; set; } + public CommunicationUnit EndUnit { get; set; } public int GapNumber { get; set; } } /// /// 可以调过多少数量的地址,把两个地址段变为一组通讯 /// - public class AddressCombinerNumericJump : AddressCombinerContinus + public class AddressCombinerNumericJump : AddressCombinerNumericJump + { + public AddressCombinerNumericJump(int jumpByteCount, AddressTranslator addressTranslator) + : base(jumpByteCount, addressTranslator) + { + } + } + + /// + /// 可以调过多少数量的地址,把两个地址段变为一组通讯 + /// + public class AddressCombinerNumericJump : AddressCombinerContinus where TKey : IEquatable { public AddressCombinerNumericJump(int jumpByteCount, AddressTranslator addressTranslator) : base(addressTranslator) @@ -189,11 +224,11 @@ namespace Modbus.Net private int JumpNumber { get; } - public override IEnumerable Combine(IEnumerable addresses) + public override IEnumerable> Combine(IEnumerable> addresses) { var continusAddresses = base.Combine(addresses).ToList(); - var addressesGaps = new List(); - CommunicationUnit preCommunicationUnit = null; + var addressesGaps = new List>(); + CommunicationUnit preCommunicationUnit = null; foreach (var continusAddress in continusAddresses) { if (preCommunicationUnit == null) @@ -204,7 +239,7 @@ namespace Modbus.Net if (continusAddress.Area == preCommunicationUnit.Area) { //计算间隔 - var gap = new CommunicationUnitGap + var gap = new CommunicationUnitGap { EndUnit = continusAddress, GapNumber = @@ -234,7 +269,7 @@ namespace Modbus.Net continusAddresses.RemoveAt(index); continusAddresses.RemoveAt(index); //合并两个已有的地址段,变为一个新的地址段 - var newAddress = new CommunicationUnit + var newAddress = new CommunicationUnit { Area = nowAddress.Area, Address = preAddress.Address, @@ -256,7 +291,18 @@ namespace Modbus.Net /// /// 可以调过多少百分比的地址,把两个地址段变为一个 /// - public class AddressCombinerPercentageJump : AddressCombinerContinus + public class AddressCombinerPercentageJump : AddressCombinerPercentageJump + { + public AddressCombinerPercentageJump(double percentage, AddressTranslator addressTranslator) + : base(percentage, addressTranslator) + { + } + } + + /// + /// 可以调过多少百分比的地址,把两个地址段变为一个 + /// + public class AddressCombinerPercentageJump : AddressCombinerContinus where TKey : IEquatable { public AddressCombinerPercentageJump(double percentage, AddressTranslator addressTranslator) : base(addressTranslator) @@ -267,12 +313,13 @@ namespace Modbus.Net private double Percentage { get; } - public override IEnumerable Combine(IEnumerable addresses) + public override IEnumerable> Combine(IEnumerable> addresses) { - var addressUnits = addresses as IList ?? addresses.ToList(); + var addressUnits = addresses as IList> ?? addresses.ToList(); var count = addressUnits.Sum(address => BigEndianValueHelper.Instance.ByteLength[address.DataType.FullName]); return - new AddressCombinerNumericJump((int) (count*Percentage/100.0), AddressTranslator).Combine(addressUnits); + new AddressCombinerNumericJump((int) (count*Percentage/100.0), AddressTranslator).Combine( + addressUnits); } } } \ No newline at end of file diff --git a/Modbus.Net/Modbus.Net/BaseMachine.cs b/Modbus.Net/Modbus.Net/BaseMachine.cs index 07b1af6..deb640e 100644 --- a/Modbus.Net/Modbus.Net/BaseMachine.cs +++ b/Modbus.Net/Modbus.Net/BaseMachine.cs @@ -23,7 +23,12 @@ namespace Modbus.Net /// /// 名称 /// - Name + Name, + + /// + /// Id + /// + Id } /// @@ -44,10 +49,33 @@ namespace Modbus.Net /// /// 名称 /// - Name + Name, + + /// + /// Id + /// + Id } - public abstract class BaseMachine : IMachineProperty + public abstract class BaseMachine : BaseMachine + { + protected BaseMachine(IEnumerable> getAddresses) : base(getAddresses) + { + } + + protected BaseMachine(IEnumerable> getAddresses, bool keepConnect) + : base(getAddresses, keepConnect) + { + } + + protected BaseMachine(IEnumerable> getAddresses, bool keepConnect, byte slaveAddress, + byte masterAddress) : base(getAddresses, keepConnect, slaveAddress, masterAddress) + { + } + } + + public abstract class BaseMachine : IMachineProperty where TKey : IEquatable + where TUnitKey : IEquatable { private readonly int _maxErrorCount = 3; @@ -55,7 +83,7 @@ namespace Modbus.Net /// 构造器 /// /// 需要与设备通讯的地址 - protected BaseMachine(IEnumerable getAddresses) + protected BaseMachine(IEnumerable> getAddresses) : this(getAddresses, false) { } @@ -65,7 +93,7 @@ namespace Modbus.Net /// /// 需要与设备通讯的地址 /// 是否保持连接 - protected BaseMachine(IEnumerable getAddresses, bool keepConnect) + protected BaseMachine(IEnumerable> getAddresses, bool keepConnect) { GetAddresses = getAddresses; KeepConnect = keepConnect; @@ -78,7 +106,7 @@ namespace Modbus.Net /// 是否保持连接 /// 从站地址 /// 主站地址 - protected BaseMachine(IEnumerable getAddresses, bool keepConnect, byte slaveAddress, + protected BaseMachine(IEnumerable> getAddresses, bool keepConnect, byte slaveAddress, byte masterAddress) : this(getAddresses, keepConnect) { SlaveAddress = slaveAddress; @@ -100,12 +128,12 @@ namespace Modbus.Net /// /// 获取地址组合器 /// - public AddressCombiner AddressCombiner { get; set; } + public AddressCombiner AddressCombiner { get; set; } /// /// 写入地址组合器 /// - public AddressCombiner AddressCombinerSet { get; set; } + public AddressCombiner AddressCombinerSet { get; set; } /// /// 地址转换器 @@ -119,13 +147,13 @@ namespace Modbus.Net /// /// 与设备实际通讯的连续地址 /// - protected IEnumerable CommunicateAddresses + protected IEnumerable> CommunicateAddresses => GetAddresses != null ? AddressCombiner.Combine(GetAddresses) : null; /// /// 描述需要与设备通讯的地址 /// - public IEnumerable GetAddresses { get; set; } + public IEnumerable> GetAddresses { get; set; } /// /// 是否保持连接 @@ -150,7 +178,7 @@ namespace Modbus.Net /// /// 设备的Id /// - public string Id { get; set; } + public TKey Id { get; set; } /// /// 设备所在工程的名称 @@ -248,6 +276,11 @@ namespace Modbus.Net key = address.Name; break; } + case MachineGetDataType.Id: + { + key = address.Id.ToString(); + break; + } default: { key = address.CommunicationTag; @@ -330,12 +363,12 @@ namespace Modbus.Net } //如果设备无法连接,终止 if (!BaseUtility.IsConnected) return false; - var addresses = new List(); + var addresses = new List>(); //遍历每个要设置的值 foreach (var value in values) { //根据设置类型找到对应的地址描述 - AddressUnit address = null; + AddressUnit address = null; switch (setDataType) { case MachineSetDataType.Address: @@ -359,6 +392,17 @@ namespace Modbus.Net address = GetAddresses.SingleOrDefault(p => p.Name == value.Key); break; } + case MachineSetDataType.Id: + { + address = GetAddresses.SingleOrDefault(p => p.Id.ToString() == value.Key); + break; + } + default: + { + address = + GetAddresses.SingleOrDefault(p => p.CommunicationTag == value.Key); + break; + } } //地址为空报错 if (address == null) @@ -433,38 +477,44 @@ namespace Modbus.Net communicateAddress.Address + (int) localPos); //获取写入类型 var dataType = addressUnit.DataType; + KeyValuePair value; switch (setDataType) { case MachineSetDataType.Address: { //获取要写入的值 - var value = + value = values.SingleOrDefault( p => p.Key == address || (address2 != null && p.Key == address2)); - //将要写入的值加入队列 - var data = Convert.ChangeType(value.Value/addressUnit.Zoom, dataType); - - if (!valueHelper.SetValue(datas, mainByteCount, localByteCount, data)) - return false; break; } case MachineSetDataType.CommunicationTag: { - var value = values.SingleOrDefault(p => p.Key == addressUnit.CommunicationTag); - var data = Convert.ChangeType(value.Value/addressUnit.Zoom, dataType); - if (!valueHelper.SetValue(datas, mainByteCount, localByteCount, data)) - return false; + value = values.SingleOrDefault(p => p.Key == addressUnit.CommunicationTag); break; } case MachineSetDataType.Name: { - var value = values.SingleOrDefault(p => p.Key == addressUnit.Name); - var data = Convert.ChangeType(value.Value/addressUnit.Zoom, dataType); - if (!valueHelper.SetValue(datas, mainByteCount, localByteCount, data)) - return false; + value = values.SingleOrDefault(p => p.Key == addressUnit.Name); + break; + } + case MachineSetDataType.Id: + { + value = values.SingleOrDefault(p => p.Key == addressUnit.Id.ToString()); + break; + } + default: + { + value = values.SingleOrDefault(p => p.Key == addressUnit.CommunicationTag); break; } } + //将要写入的值加入队列 + var data = Convert.ChangeType(value.Value/addressUnit.Zoom, dataType); + + if (!valueHelper.SetValue(datas, mainByteCount, localByteCount, data)) + return false; + break; } //写入数据 await @@ -486,6 +536,19 @@ namespace Modbus.Net return true; } + public AddressUnit GetAddressUnitById(TUnitKey addressUnitId) + { + try + { + return GetAddresses.SingleOrDefault(p => p.Id.Equals(addressUnitId)); + } + catch (Exception) + { + Console.WriteLine("Id重复,请检查"); + return null; + } + } + /// /// 连接设备 /// @@ -514,14 +577,15 @@ namespace Modbus.Net } } - public class BaseMachineEqualityComparer : IEqualityComparer + public class BaseMachineEqualityComparer : IEqualityComparer> + where TKey : IEquatable where TUnitKey : IEquatable { - public bool Equals(BaseMachine x, BaseMachine y) + public bool Equals(BaseMachine x, BaseMachine y) { return x.ConnectionToken == y.ConnectionToken; } - public int GetHashCode(BaseMachine obj) + public int GetHashCode(BaseMachine obj) { return obj.GetHashCode(); } @@ -530,7 +594,14 @@ namespace Modbus.Net /// /// 通讯单元 /// - public class CommunicationUnit + public class CommunicationUnit : CommunicationUnit + { + } + + /// + /// 通讯单元 + /// + public class CommunicationUnit where TKey : IEquatable { /// /// 区域 @@ -560,7 +631,7 @@ namespace Modbus.Net /// /// 原始的地址 /// - public IEnumerable OriginalAddresses { get; set; } + public IEnumerable> OriginalAddresses { get; set; } } /// @@ -586,12 +657,22 @@ namespace Modbus.Net public UnitExtend UnitExtend { get; set; } } - public class AddressUnit + /// + /// 地址单元 + /// + public class AddressUnit : AddressUnit + { + } + + /// + /// 地址单元 + /// + public class AddressUnit where TKey : IEquatable { /// /// 数据单元Id /// - public string Id { get; set; } + public TKey Id { get; set; } /// /// 数据所属的区域 @@ -652,14 +733,14 @@ namespace Modbus.Net /// /// AddressUnit大小比较 /// - public struct AddressUnitEqualityComparer : IEqualityComparer + public struct AddressUnitEqualityComparer : IEqualityComparer> where TKey : IEquatable { - public bool Equals(AddressUnit x, AddressUnit y) + public bool Equals(AddressUnit x, AddressUnit y) { - return x.Area.ToUpper() == y.Area.ToUpper() && x.Address == y.Address; + return (x.Area.ToUpper() == y.Area.ToUpper() && x.Address == y.Address) || x.Id.Equals(y.Id); } - public int GetHashCode(AddressUnit obj) + public int GetHashCode(AddressUnit obj) { return obj.GetHashCode(); } @@ -668,12 +749,12 @@ namespace Modbus.Net /// /// 设备的抽象 /// - public interface IMachineProperty + public interface IMachineProperty where TKey : IEquatable { /// /// Id /// - string Id { get; set; } + TKey Id { get; set; } /// /// 工程名 diff --git a/Modbus.Net/Modbus.Net/ModBus.Net.nuspec b/Modbus.Net/Modbus.Net/ModBus.Net.nuspec index 723cc37..a66ad0c 100644 --- a/Modbus.Net/Modbus.Net/ModBus.Net.nuspec +++ b/Modbus.Net/Modbus.Net/ModBus.Net.nuspec @@ -2,7 +2,7 @@ Modbus.Net - 1.2.3.1 + 1.2.3.2 Modbus.Net Chris L.(Luo Sheng) Hangzhou Delian IoT Science Technology Co.,Ltd. diff --git a/Modbus.Net/Modbus.Net/TaskManager.cs b/Modbus.Net/Modbus.Net/TaskManager.cs index 38128a8..5b39cb6 100644 --- a/Modbus.Net/Modbus.Net/TaskManager.cs +++ b/Modbus.Net/Modbus.Net/TaskManager.cs @@ -18,15 +18,16 @@ namespace Modbus.Net { Address, CommunicationTag, - Name + Name, + Id } /// /// 返回结果的定义类 /// - public class TaskReturnDef + public class TaskReturnDef where TMachineKey : IEquatable { - public string MachineId { get; set; } + public TMachineKey MachineId { get; set; } public Dictionary ReturnValues { get; set; } } @@ -197,23 +198,41 @@ namespace Modbus.Net } } - public class TaskManager + /// + /// 任务调度器 + /// + public class TaskManager : TaskManager + { + public TaskManager(int maxRunningTask, int getCycle, bool keepConnect, + MachineDataType dataType = MachineDataType.CommunicationTag) + : base(maxRunningTask, getCycle, keepConnect, dataType) + { + } + } + + /// + /// 任务调度器 + /// + /// + /// + public class TaskManager where TMachineKey : IEquatable + where TUnitKey : IEquatable { /// /// 返回数据代理 /// /// - public delegate void ReturnValuesDelegate(TaskReturnDef returnValue); + public delegate void ReturnValuesDelegate(TaskReturnDef returnValue); /// /// 正在运行的设备 /// - private readonly HashSet _machines; + private readonly HashSet> _machines; /// /// 不在运行的设备 /// - private readonly HashSet _unlinkedMachines; + private readonly HashSet> _unlinkedMachines; private CancellationTokenSource _cts; @@ -258,8 +277,10 @@ namespace Modbus.Net MachineDataType dataType = MachineDataType.CommunicationTag) { _scheduler = new LimitedConcurrencyLevelTaskScheduler(maxRunningTask); - _machines = new HashSet(new BaseMachineEqualityComparer()); - _unlinkedMachines = new HashSet(new BaseMachineEqualityComparer()); + _machines = + new HashSet>(new BaseMachineEqualityComparer()); + _unlinkedMachines = + new HashSet>(new BaseMachineEqualityComparer()); _getCycle = getCycle; KeepConnect = keepConnect; MachineDataType = dataType; @@ -355,6 +376,12 @@ namespace Modbus.Net SetDataType = MachineSetDataType.Name; break; } + case MachineDataType.Id: + { + GetDataType = MachineGetDataType.Id; + SetDataType = MachineSetDataType.Id; + break; + } } } } @@ -384,7 +411,7 @@ namespace Modbus.Net /// 添加一台设备 /// /// 设备 - public void AddMachine(BaseMachine machine) + public void AddMachine(BaseMachine machine) { machine.KeepConnect = KeepConnect; lock (_machines) @@ -397,7 +424,7 @@ namespace Modbus.Net /// 添加多台设备 /// /// 设备的列表 - public void AddMachines(IEnumerable machines) + public void AddMachines(IEnumerable> machines) { lock (_machines) { @@ -428,15 +455,15 @@ namespace Modbus.Net /// 根据设备的id移除设备 /// /// 设备的id - public void RemoveMachineWithId(string id) + public void RemoveMachineWithId(TMachineKey id) { lock (_machines) { - _machines.RemoveWhere(p => p.Id == id); + _machines.RemoveWhere(p => p.Id.Equals(id)); } lock (_unlinkedMachines) { - _unlinkedMachines.RemoveWhere(p => p.Id == id); + _unlinkedMachines.RemoveWhere(p => p.Id.Equals(id)); } } @@ -444,14 +471,14 @@ namespace Modbus.Net /// 将设备指定为未连接 /// /// 设备的id - public void MoveMachineToUnlinked(string id) + public void MoveMachineToUnlinked(TMachineKey id) { - IEnumerable machines; + IEnumerable> machines; lock (_machines) { - machines = _machines.Where(c => c.Id == id).ToList(); + machines = _machines.Where(c => c.Id.Equals(id)).ToList(); if (!machines.Any()) return; - _machines.RemoveWhere(p => p.Id == id); + _machines.RemoveWhere(p => p.Id.Equals(id)); } lock (_unlinkedMachines) { @@ -466,14 +493,14 @@ namespace Modbus.Net /// 将设备指定为已连接 /// /// 设备的id - public void MoveMachineToLinked(string id) + public void MoveMachineToLinked(TMachineKey id) { - IEnumerable machines; + IEnumerable> machines; lock (_unlinkedMachines) { - machines = _unlinkedMachines.Where(c => c.Id == id).ToList(); + machines = _unlinkedMachines.Where(c => c.Id.Equals(id)).ToList(); if (!machines.Any()) return; - _unlinkedMachines.RemoveWhere(p => p.Id == id); + _unlinkedMachines.RemoveWhere(p => p.Id.Equals(id)); } lock (_machines) { @@ -488,7 +515,7 @@ namespace Modbus.Net /// 移除设备 /// /// 设备的实例 - public void RemoveMachine(BaseMachine machine) + public void RemoveMachine(BaseMachine machine) { lock (_machines) { @@ -527,8 +554,8 @@ namespace Modbus.Net try { var tasks = new List(); - var saveMachines = new HashSet(); - IEnumerable saveMachinesEnum; + var saveMachines = new HashSet>(); + IEnumerable> saveMachinesEnum; lock (_machines) { saveMachines.UnionWith(_machines); @@ -543,7 +570,7 @@ namespace Modbus.Net } await Task.WhenAll(tasks); } - catch(Exception) + catch (Exception) { //ignore } @@ -558,7 +585,7 @@ namespace Modbus.Net try { var tasks = new List(); - var saveMachines = new HashSet(); + var saveMachines = new HashSet>(); lock (_unlinkedMachines) { saveMachines.UnionWith(_unlinkedMachines); @@ -572,7 +599,7 @@ namespace Modbus.Net } await Task.WhenAll(tasks); } - catch(Exception) + catch (Exception) { //ignore } @@ -587,7 +614,7 @@ namespace Modbus.Net public async Task SetDatasAsync(string connectionToken, Dictionary values) { - BaseMachine machine = null; + BaseMachine machine = null; lock (_machines) { machine = _machines.FirstOrDefault(p => p.ConnectionToken == connectionToken); @@ -632,7 +659,7 @@ namespace Modbus.Net /// /// 设备的实例 /// - private async Task RunTask(BaseMachine machine) + private async Task RunTask(BaseMachine machine) { try { @@ -652,7 +679,7 @@ namespace Modbus.Net { MoveMachineToLinked(machine.Id); } - ReturnValues?.Invoke(new TaskReturnDef + ReturnValues?.Invoke(new TaskReturnDef { MachineId = machine.Id, ReturnValues = ans @@ -664,7 +691,7 @@ namespace Modbus.Net { MoveMachineToUnlinked(machine.Id); } - ReturnValues?.Invoke(new TaskReturnDef + ReturnValues?.Invoke(new TaskReturnDef { MachineId = machine.Id, ReturnValues = null