745 lines
20 KiB
C#
745 lines
20 KiB
C#
using OrpaonVision.Core.LayerRecognition;
|
|
using OrpaonVision.Core.PartRecognition;
|
|
using OrpaonVision.Core.Results;
|
|
|
|
namespace OrpaonVision.Core.QuantityValidation;
|
|
|
|
/// <summary>
|
|
/// 数量校验服务接口。
|
|
/// </summary>
|
|
public interface IQuantityValidationService
|
|
{
|
|
/// <summary>
|
|
/// 校验精确数量。
|
|
/// </summary>
|
|
/// <param name="parts">部件列表。</param>
|
|
/// <param name="expectedCount">期望数量。</param>
|
|
/// <param name="partType">部件类型(可选)。</param>
|
|
/// <param name="cancellationToken">取消令牌。</param>
|
|
/// <returns>精确数量校验结果。</returns>
|
|
Task<Result<ExactQuantityValidationResult>> ValidateExactQuantityAsync(IReadOnlyList<MappedPart> parts, int expectedCount, PartType? partType = null, CancellationToken cancellationToken = default);
|
|
|
|
/// <summary>
|
|
/// 校验最少数量。
|
|
/// </summary>
|
|
/// <param name="parts">部件列表。</param>
|
|
/// <param name="minCount">最少数量。</param>
|
|
/// <param name="partType">部件类型(可选)。</param>
|
|
/// <param name="cancellationToken">取消令牌。</param>
|
|
/// <returns>最少数量校验结果。</returns>
|
|
Task<Result<MinimumQuantityValidationResult>> ValidateMinimumQuantityAsync(IReadOnlyList<MappedPart> parts, int minCount, PartType? partType = null, CancellationToken cancellationToken = default);
|
|
|
|
/// <summary>
|
|
/// 校验范围数量。
|
|
/// </summary>
|
|
/// <param name="parts">部件列表。</param>
|
|
/// <param name="minCount">最小数量。</param>
|
|
/// <param name="maxCount">最大数量。</param>
|
|
/// <param name="partType">部件类型(可选)。</param>
|
|
/// <param name="cancellationToken">取消令牌。</param>
|
|
/// <returns>范围数量校验结果。</returns>
|
|
Task<Result<RangeQuantityValidationResult>> ValidateRangeQuantityAsync(IReadOnlyList<MappedPart> parts, int minCount, int maxCount, PartType? partType = null, CancellationToken cancellationToken = default);
|
|
|
|
/// <summary>
|
|
/// 校验唯一数量。
|
|
/// </summary>
|
|
/// <param name="parts">部件列表。</param>
|
|
/// <param name="uniqueProperty">唯一属性名。</param>
|
|
/// <param name="expectedUniqueCount">期望唯一数量。</param>
|
|
/// <param name="partType">部件类型(可选)。</param>
|
|
/// <param name="cancellationToken">取消令牌。</param>
|
|
/// <returns>唯一数量校验结果。</returns>
|
|
Task<Result<UniqueQuantityValidationResult>> ValidateUniqueQuantityAsync(IReadOnlyList<MappedPart> parts, string uniqueProperty, int expectedUniqueCount, PartType? partType = null, CancellationToken cancellationToken = default);
|
|
|
|
/// <summary>
|
|
/// 批量数量校验。
|
|
/// </summary>
|
|
/// <param name="parts">部件列表。</param>
|
|
/// <param name="validationRules">校验规则列表。</param>
|
|
/// <param name="cancellationToken">取消令牌。</param>
|
|
/// <returns>批量校验结果。</returns>
|
|
Task<Result<BatchQuantityValidationResult>> BatchValidateQuantityAsync(IReadOnlyList<MappedPart> parts, IReadOnlyList<QuantityValidationRule> validationRules, CancellationToken cancellationToken = default);
|
|
|
|
/// <summary>
|
|
/// 获取数量校验统计信息。
|
|
/// </summary>
|
|
/// <param name="startTime">开始时间。</param>
|
|
/// <param name="endTime">结束时间。</param>
|
|
/// <param name="cancellationToken">取消令牌。</param>
|
|
/// <returns>统计信息。</returns>
|
|
Task<Result<QuantityValidationStatistics>> GetValidationStatisticsAsync(DateTime startTime, DateTime endTime, CancellationToken cancellationToken = default);
|
|
|
|
/// <summary>
|
|
/// 创建数量校验规则。
|
|
/// </summary>
|
|
/// <param name="rule">校验规则。</param>
|
|
/// <param name="cancellationToken">取消令牌。</param>
|
|
/// <returns>创建结果。</returns>
|
|
Task<Result<QuantityValidationRule>> CreateValidationRuleAsync(QuantityValidationRule rule, CancellationToken cancellationToken = default);
|
|
|
|
/// <summary>
|
|
/// 更新数量校验规则。
|
|
/// </summary>
|
|
/// <param name="rule">校验规则。</param>
|
|
/// <param name="cancellationToken">取消令牌。</param>
|
|
/// <returns>更新结果。</returns>
|
|
Task<Result> UpdateValidationRuleAsync(QuantityValidationRule rule, CancellationToken cancellationToken = default);
|
|
|
|
/// <summary>
|
|
/// 删除数量校验规则。
|
|
/// </summary>
|
|
/// <param name="ruleId">规则ID。</param>
|
|
/// <param name="cancellationToken">取消令牌。</param>
|
|
/// <returns>删除结果。</returns>
|
|
Task<Result> DeleteValidationRuleAsync(Guid ruleId, CancellationToken cancellationToken = default);
|
|
|
|
/// <summary>
|
|
/// 获取数量校验规则列表。
|
|
/// </summary>
|
|
/// <param name="productTypeCode">产品类型编码(可选)。</param>
|
|
/// <param name="layerNumber">层级编号(可选)。</param>
|
|
/// <param name="partType">部件类型(可选)。</param>
|
|
/// <param name="cancellationToken">取消令牌。</param>
|
|
/// <returns>规则列表。</returns>
|
|
Task<Result<IReadOnlyList<QuantityValidationRule>>> GetValidationRulesAsync(string? productTypeCode = null, int? layerNumber = null, PartType? partType = null, CancellationToken cancellationToken = default);
|
|
}
|
|
|
|
/// <summary>
|
|
/// 精确数量校验结果。
|
|
/// </summary>
|
|
public sealed class ExactQuantityValidationResult
|
|
{
|
|
/// <summary>
|
|
/// 是否通过校验。
|
|
/// </summary>
|
|
public bool IsValid { get; init; }
|
|
|
|
/// <summary>
|
|
/// 实际数量。
|
|
/// </summary>
|
|
public int ActualCount { get; init; }
|
|
|
|
/// <summary>
|
|
/// 期望数量。
|
|
/// </summary>
|
|
public int ExpectedCount { get; init; }
|
|
|
|
/// <summary>
|
|
/// 数量偏差。
|
|
/// </summary>
|
|
public int Deviation => ActualCount - ExpectedCount;
|
|
|
|
/// <summary>
|
|
/// 部件类型(如果指定)。
|
|
/// </summary>
|
|
public PartType? PartType { get; init; }
|
|
|
|
/// <summary>
|
|
/// 匹配的部件列表。
|
|
/// </summary>
|
|
public IReadOnlyList<MappedPart> MatchedParts { get; init; } = Array.Empty<MappedPart>();
|
|
|
|
/// <summary>
|
|
/// 校验时间。
|
|
/// </summary>
|
|
public DateTime ValidationTimeUtc { get; init; }
|
|
|
|
/// <summary>
|
|
/// 详细信息。
|
|
/// </summary>
|
|
public string? Details { get; init; }
|
|
|
|
/// <summary>
|
|
/// 扩展属性。
|
|
/// </summary>
|
|
public Dictionary<string, object> ExtendedProperties { get; init; } = new();
|
|
}
|
|
|
|
/// <summary>
|
|
/// 最少数量校验结果。
|
|
/// </summary>
|
|
public sealed class MinimumQuantityValidationResult
|
|
{
|
|
/// <summary>
|
|
/// 是否通过校验。
|
|
/// </summary>
|
|
public bool IsValid { get; init; }
|
|
|
|
/// <summary>
|
|
/// 实际数量。
|
|
/// </summary>
|
|
public int ActualCount { get; init; }
|
|
|
|
/// <summary>
|
|
/// 最少数量。
|
|
/// </summary>
|
|
public int MinimumCount { get; init; }
|
|
|
|
/// <summary>
|
|
/// 超出数量。
|
|
/// </summary>
|
|
public int ExcessCount => Math.Max(0, ActualCount - MinimumCount);
|
|
|
|
/// <summary>
|
|
/// 部件类型(如果指定)。
|
|
/// </summary>
|
|
public PartType? PartType { get; init; }
|
|
|
|
/// <summary>
|
|
/// 匹配的部件列表。
|
|
/// </summary>
|
|
public IReadOnlyList<MappedPart> MatchedParts { get; init; } = Array.Empty<MappedPart>();
|
|
|
|
/// <summary>
|
|
/// 校验时间。
|
|
/// </summary>
|
|
public DateTime ValidationTimeUtc { get; init; }
|
|
|
|
/// <summary>
|
|
/// 详细信息。
|
|
/// </summary>
|
|
public string? Details { get; init; }
|
|
|
|
/// <summary>
|
|
/// 扩展属性。
|
|
/// </summary>
|
|
public Dictionary<string, object> ExtendedProperties { get; init; } = new();
|
|
}
|
|
|
|
/// <summary>
|
|
/// 范围数量校验结果。
|
|
/// </summary>
|
|
public sealed class RangeQuantityValidationResult
|
|
{
|
|
/// <summary>
|
|
/// 是否通过校验。
|
|
/// </summary>
|
|
public bool IsValid { get; init; }
|
|
|
|
/// <summary>
|
|
/// 实际数量。
|
|
/// </summary>
|
|
public int ActualCount { get; init; }
|
|
|
|
/// <summary>
|
|
/// 最小数量。
|
|
/// </summary>
|
|
public int MinimumCount { get; init; }
|
|
|
|
/// <summary>
|
|
/// 最大数量。
|
|
/// </summary>
|
|
public int MaximumCount { get; init; }
|
|
|
|
/// <summary>
|
|
/// 是否低于最小值。
|
|
/// </summary>
|
|
public bool IsBelowMinimum => ActualCount < MinimumCount;
|
|
|
|
/// <summary>
|
|
/// 是否高于最大值。
|
|
/// </summary>
|
|
public bool IsAboveMaximum => ActualCount > MaximumCount;
|
|
|
|
/// <summary>
|
|
/// 部件类型(如果指定)。
|
|
/// </summary>
|
|
public PartType? PartType { get; init; }
|
|
|
|
/// <summary>
|
|
/// 匹配的部件列表。
|
|
/// </summary>
|
|
public IReadOnlyList<MappedPart> MatchedParts { get; init; } = Array.Empty<MappedPart>();
|
|
|
|
/// <summary>
|
|
/// 校验时间。
|
|
/// </summary>
|
|
public DateTime ValidationTimeUtc { get; init; }
|
|
|
|
/// <summary>
|
|
/// 详细信息。
|
|
/// </summary>
|
|
public string? Details { get; init; }
|
|
|
|
/// <summary>
|
|
/// 扩展属性。
|
|
/// </summary>
|
|
public Dictionary<string, object> ExtendedProperties { get; init; } = new();
|
|
}
|
|
|
|
/// <summary>
|
|
/// 唯一数量校验结果。
|
|
/// </summary>
|
|
public sealed class UniqueQuantityValidationResult
|
|
{
|
|
/// <summary>
|
|
/// 是否通过校验。
|
|
/// </summary>
|
|
public bool IsValid { get; init; }
|
|
|
|
/// <summary>
|
|
/// 实际唯一数量。
|
|
/// </summary>
|
|
public int ActualUniqueCount { get; init; }
|
|
|
|
/// <summary>
|
|
/// 期望唯一数量。
|
|
/// </summary>
|
|
public int ExpectedUniqueCount { get; init; }
|
|
|
|
/// <summary>
|
|
/// 唯一属性名。
|
|
/// </summary>
|
|
public string UniqueProperty { get; init; } = string.Empty;
|
|
|
|
/// <summary>
|
|
/// 唯一值列表。
|
|
/// </summary>
|
|
public IReadOnlyList<object> UniqueValues { get; init; } = Array.Empty<object>();
|
|
|
|
/// <summary>
|
|
/// 重复值列表。
|
|
/// </summary>
|
|
public IReadOnlyList<DuplicateValue> DuplicateValues { get; init; } = Array.Empty<DuplicateValue>();
|
|
|
|
/// <summary>
|
|
/// 部件类型(如果指定)。
|
|
/// </summary>
|
|
public PartType? PartType { get; init; }
|
|
|
|
/// <summary>
|
|
/// 匹配的部件列表。
|
|
/// </summary>
|
|
public IReadOnlyList<MappedPart> MatchedParts { get; init; } = Array.Empty<MappedPart>();
|
|
|
|
/// <summary>
|
|
/// 校验时间。
|
|
/// </summary>
|
|
public DateTime ValidationTimeUtc { get; init; }
|
|
|
|
/// <summary>
|
|
/// 详细信息。
|
|
/// </summary>
|
|
public string? Details { get; init; }
|
|
|
|
/// <summary>
|
|
/// 扩展属性。
|
|
/// </summary>
|
|
public Dictionary<string, object> ExtendedProperties { get; init; } = new();
|
|
}
|
|
|
|
/// <summary>
|
|
/// 重复值信息。
|
|
/// </summary>
|
|
public sealed class DuplicateValue
|
|
{
|
|
/// <summary>
|
|
/// 重复值。
|
|
/// </summary>
|
|
public object Value { get; init; } = string.Empty;
|
|
|
|
/// <summary>
|
|
/// 出现次数。
|
|
/// </summary>
|
|
public int Count { get; init; }
|
|
|
|
/// <summary>
|
|
/// 相关部件ID列表。
|
|
/// </summary>
|
|
public IReadOnlyList<Guid> PartIds { get; init; } = Array.Empty<Guid>();
|
|
}
|
|
|
|
/// <summary>
|
|
/// 批量数量校验结果。
|
|
/// </summary>
|
|
public sealed class BatchQuantityValidationResult
|
|
{
|
|
/// <summary>
|
|
/// 校验结果列表。
|
|
/// </summary>
|
|
public IReadOnlyList<QuantityValidationResult> ValidationResults { get; init; } = Array.Empty<QuantityValidationResult>();
|
|
|
|
/// <summary>
|
|
/// 总规则数量。
|
|
/// </summary>
|
|
public int TotalRules { get; init; }
|
|
|
|
/// <summary>
|
|
/// 通过的规则数量。
|
|
/// </summary>
|
|
public int PassedRules { get; init; }
|
|
|
|
/// <summary>
|
|
/// 失败的规则数量。
|
|
/// </summary>
|
|
public int FailedRules { get; init; }
|
|
|
|
/// <summary>
|
|
/// 总体通过率。
|
|
/// </summary>
|
|
public double OverallPassRate => TotalRules > 0 ? (double)PassedRules / TotalRules * 100 : 0.0;
|
|
|
|
/// <summary>
|
|
/// 批量处理时间。
|
|
/// </summary>
|
|
public DateTime BatchProcessingTimeUtc { get; init; }
|
|
|
|
/// <summary>
|
|
/// 总耗时(毫秒)。
|
|
/// </summary>
|
|
public long TotalElapsedMs { get; init; }
|
|
|
|
/// <summary>
|
|
/// 详细信息。
|
|
/// </summary>
|
|
public string? Details { get; init; }
|
|
|
|
/// <summary>
|
|
/// 扩展属性。
|
|
/// </summary>
|
|
public Dictionary<string, object> ExtendedProperties { get; init; } = new();
|
|
}
|
|
|
|
/// <summary>
|
|
/// 数量校验结果基类。
|
|
/// </summary>
|
|
public abstract class QuantityValidationResult
|
|
{
|
|
/// <summary>
|
|
/// 规则ID。
|
|
/// </summary>
|
|
public Guid RuleId { get; init; }
|
|
|
|
/// <summary>
|
|
/// 规则名称。
|
|
/// </summary>
|
|
public string RuleName { get; init; } = string.Empty;
|
|
|
|
/// <summary>
|
|
/// 校验类型。
|
|
/// </summary>
|
|
public QuantityValidationType ValidationType { get; init; }
|
|
|
|
/// <summary>
|
|
/// 是否通过校验。
|
|
/// </summary>
|
|
public bool IsValid { get; init; }
|
|
|
|
/// <summary>
|
|
/// 校验时间。
|
|
/// </summary>
|
|
public DateTime ValidationTimeUtc { get; init; }
|
|
|
|
/// <summary>
|
|
/// 错误消息。
|
|
/// </summary>
|
|
public string? ErrorMessage { get; init; }
|
|
|
|
/// <summary>
|
|
/// 扩展属性。
|
|
/// </summary>
|
|
public Dictionary<string, object> ExtendedProperties { get; init; } = new();
|
|
}
|
|
|
|
/// <summary>
|
|
/// 数量校验规则。
|
|
/// </summary>
|
|
public sealed class QuantityValidationRule
|
|
{
|
|
/// <summary>
|
|
/// 规则ID。
|
|
/// </summary>
|
|
public Guid RuleId { get; init; }
|
|
|
|
/// <summary>
|
|
/// 规则名称。
|
|
/// </summary>
|
|
public string RuleName { get; init; } = string.Empty;
|
|
|
|
/// <summary>
|
|
/// 规则描述。
|
|
/// </summary>
|
|
public string RuleDescription { get; init; } = string.Empty;
|
|
|
|
/// <summary>
|
|
/// 产品类型编码。
|
|
/// </summary>
|
|
public string ProductTypeCode { get; init; } = string.Empty;
|
|
|
|
/// <summary>
|
|
/// 层级编号。
|
|
/// </summary>
|
|
public int LayerNumber { get; init; }
|
|
|
|
/// <summary>
|
|
/// 部件类型(可选)。
|
|
/// </summary>
|
|
public PartType? PartType { get; init; }
|
|
|
|
/// <summary>
|
|
/// 校验类型。
|
|
/// </summary>
|
|
public QuantityValidationType ValidationType { get; init; }
|
|
|
|
/// <summary>
|
|
/// 最小数量。
|
|
/// </summary>
|
|
public int MinimumCount { get; init; }
|
|
|
|
/// <summary>
|
|
/// 最大数量。
|
|
/// </summary>
|
|
public int MaximumCount { get; init; }
|
|
|
|
/// <summary>
|
|
/// 期望数量。
|
|
/// </summary>
|
|
public int ExpectedCount { get; init; }
|
|
|
|
/// <summary>
|
|
/// 唯一属性名。
|
|
/// </summary>
|
|
public string UniqueProperty { get; init; } = string.Empty;
|
|
|
|
/// <summary>
|
|
/// 期望唯一数量。
|
|
/// </summary>
|
|
public int ExpectedUniqueCount { get; init; }
|
|
|
|
/// <summary>
|
|
/// 是否启用。
|
|
/// </summary>
|
|
public bool IsEnabled { get; init; } = true;
|
|
|
|
/// <summary>
|
|
/// 优先级。
|
|
/// </summary>
|
|
public int Priority { get; init; } = 1;
|
|
|
|
/// <summary>
|
|
/// 创建时间。
|
|
/// </summary>
|
|
public DateTime CreatedAtUtc { get; init; }
|
|
|
|
/// <summary>
|
|
/// 更新时间。
|
|
/// </summary>
|
|
public DateTime UpdatedAtUtc { get; init; }
|
|
|
|
/// <summary>
|
|
/// 版本号。
|
|
/// </summary>
|
|
public string Version { get; init; } = "1.0";
|
|
|
|
/// <summary>
|
|
/// 扩展属性。
|
|
/// </summary>
|
|
public Dictionary<string, object> ExtendedProperties { get; init; } = new();
|
|
}
|
|
|
|
/// <summary>
|
|
/// 数量校验统计信息。
|
|
/// </summary>
|
|
public sealed class QuantityValidationStatistics
|
|
{
|
|
/// <summary>
|
|
/// 总校验次数。
|
|
/// </summary>
|
|
public int TotalValidations { get; init; }
|
|
|
|
/// <summary>
|
|
/// 成功校验次数。
|
|
/// </summary>
|
|
public int SuccessfulValidations { get; init; }
|
|
|
|
/// <summary>
|
|
/// 失败校验次数。
|
|
/// </summary>
|
|
public int FailedValidations { get; init; }
|
|
|
|
/// <summary>
|
|
/// 总体成功率。
|
|
/// </summary>
|
|
public double OverallSuccessRate => TotalValidations > 0 ? (double)SuccessfulValidations / TotalValidations * 100 : 0.0;
|
|
|
|
/// <summary>
|
|
/// 按校验类型分组的统计。
|
|
/// </summary>
|
|
public Dictionary<QuantityValidationType, ValidationTypeStatistics> ByValidationType { get; init; } = new();
|
|
|
|
/// <summary>
|
|
/// 按部件类型分组的统计。
|
|
/// </summary>
|
|
public Dictionary<PartType, PartTypeValidationStatistics> ByPartType { get; init; } = new();
|
|
|
|
/// <summary>
|
|
/// 按产品类型分组的统计。
|
|
/// </summary>
|
|
public Dictionary<string, ProductTypeValidationStatistics> ByProductType { get; init; } = new();
|
|
|
|
/// <summary>
|
|
/// 按层级分组的统计。
|
|
/// </summary>
|
|
public Dictionary<int, LayerValidationStatistics> ByLayer { get; init; } = new();
|
|
|
|
/// <summary>
|
|
/// 统计开始时间。
|
|
/// </summary>
|
|
public DateTime StartTimeUtc { get; init; }
|
|
|
|
/// <summary>
|
|
/// 统计结束时间。
|
|
/// </summary>
|
|
public DateTime EndTimeUtc { get; init; }
|
|
}
|
|
|
|
/// <summary>
|
|
/// 校验类型统计。
|
|
/// </summary>
|
|
public sealed class ValidationTypeStatistics
|
|
{
|
|
/// <summary>
|
|
/// 校验类型。
|
|
/// </summary>
|
|
public QuantityValidationType ValidationType { get; init; }
|
|
|
|
/// <summary>
|
|
/// 校验次数。
|
|
/// </summary>
|
|
public int ValidationCount { get; init; }
|
|
|
|
/// <summary>
|
|
/// 成功次数。
|
|
/// </summary>
|
|
public int SuccessCount { get; init; }
|
|
|
|
/// <summary>
|
|
/// 成功率。
|
|
/// </summary>
|
|
public double SuccessRate => ValidationCount > 0 ? (double)SuccessCount / ValidationCount * 100 : 0.0;
|
|
|
|
/// <summary>
|
|
/// 平均耗时(毫秒)。
|
|
/// </summary>
|
|
public double AverageElapsedMs { get; init; }
|
|
}
|
|
|
|
/// <summary>
|
|
/// 部件类型校验统计。
|
|
/// </summary>
|
|
public sealed class PartTypeValidationStatistics
|
|
{
|
|
/// <summary>
|
|
/// 部件类型。
|
|
/// </summary>
|
|
public PartType PartType { get; init; }
|
|
|
|
/// <summary>
|
|
/// 校验次数。
|
|
/// </summary>
|
|
public int ValidationCount { get; init; }
|
|
|
|
/// <summary>
|
|
/// 成功次数。
|
|
/// </summary>
|
|
public int SuccessCount { get; init; }
|
|
|
|
/// <summary>
|
|
/// 成功率。
|
|
/// </summary>
|
|
public double SuccessRate => ValidationCount > 0 ? (double)SuccessCount / ValidationCount * 100 : 0.0;
|
|
|
|
/// <summary>
|
|
/// 平均部件数量。
|
|
/// </summary>
|
|
public double AveragePartCount { get; init; }
|
|
}
|
|
|
|
/// <summary>
|
|
/// 产品类型校验统计。
|
|
/// </summary>
|
|
public sealed class ProductTypeValidationStatistics
|
|
{
|
|
/// <summary>
|
|
/// 产品类型编码。
|
|
/// </summary>
|
|
public string ProductTypeCode { get; init; } = string.Empty;
|
|
|
|
/// <summary>
|
|
/// 校验次数。
|
|
/// </summary>
|
|
public int ValidationCount { get; init; }
|
|
|
|
/// <summary>
|
|
/// 成功次数。
|
|
/// </summary>
|
|
public int SuccessCount { get; init; }
|
|
|
|
/// <summary>
|
|
/// 成功率。
|
|
/// </summary>
|
|
public double SuccessRate => ValidationCount > 0 ? (double)SuccessCount / ValidationCount * 100 : 0.0;
|
|
|
|
/// <summary>
|
|
/// 平均部件数量。
|
|
/// </summary>
|
|
public double AveragePartCount { get; init; }
|
|
}
|
|
|
|
/// <summary>
|
|
/// 层级校验统计。
|
|
/// </summary>
|
|
public sealed class LayerValidationStatistics
|
|
{
|
|
/// <summary>
|
|
/// 层级编号。
|
|
/// </summary>
|
|
public int LayerNumber { get; init; }
|
|
|
|
/// <summary>
|
|
/// 校验次数。
|
|
/// </summary>
|
|
public int ValidationCount { get; init; }
|
|
|
|
/// <summary>
|
|
/// 成功次数。
|
|
/// </summary>
|
|
public int SuccessCount { get; init; }
|
|
|
|
/// <summary>
|
|
/// 成功率。
|
|
/// </summary>
|
|
public double SuccessRate => ValidationCount > 0 ? (double)SuccessCount / ValidationCount * 100 : 0.0;
|
|
|
|
/// <summary>
|
|
/// 平均部件数量。
|
|
/// </summary>
|
|
public double AveragePartCount { get; init; }
|
|
}
|
|
|
|
/// <summary>
|
|
/// 数量校验类型枚举。
|
|
/// </summary>
|
|
public enum QuantityValidationType
|
|
{
|
|
/// <summary>
|
|
/// 精确数量。
|
|
/// </summary>
|
|
Exact = 0,
|
|
|
|
/// <summary>
|
|
/// 最少数量。
|
|
/// </summary>
|
|
Minimum = 1,
|
|
|
|
/// <summary>
|
|
/// 范围数量。
|
|
/// </summary>
|
|
Range = 2,
|
|
|
|
/// <summary>
|
|
/// 唯一数量。
|
|
/// </summary>
|
|
Unique = 3
|
|
}
|