【发布时间】:2021-12-01 11:17:44
【问题描述】:
我有下面的对象及其内部对象,并且我已将自定义属性添加到报告所需的属性名称中。
public class Space
{
public SpaceIdentity SpaceIdentity { get; set; } = new();
public SpaceGeometry SpaceGeometry { get; set; } = new();
public AirBalance AirBalance { get; set; } = new();
public EngineeringChecks EngineeringChecks { get; set; } = new();
}
public class SpaceIdentity
{
public int ElementId { get; set; } // Not required
[DisplayNameWithUnits(DisplayName = "Space Number", IsIncludedInReport2 = true)]
public string Number { get; set; }
[DisplayNameWithUnits(DisplayName = "Space Name", IsIncludedInReport2 = true, IsIncludedInReport1 = true)]
public string Name { get; set; }
[DisplayNameWithUnits(DisplayName = "Room Number", IsIncludedInReport1 = true)]
public string RoomNumber { get; set; }
[DisplayNameWithUnits(DisplayName = "Room Name", IsIncludedInReport1 = true)]
public string RoomName { get; set; }
}
public class SpaceGeometry
{
public Vertex LocationPoint { get; set; } // this is not required
[DisplayNameWithUnits(DisplayName = "Space Area", Units = "(ft²)", IsIncludedInReport1 = true)]
public double FloorArea { get; set; }
}
.....
在这里,我正在构建一个 Excel 报表,我想使用属性显示名称作为该报表的标题列名称。以下是多个报告中使用的一些属性属性信息。我所做的是我添加了一个布尔条件属性,如 (isIncludedInReport1) 并循环遍历 space 的属性并循环遍历内部对象的属性 (SpaceGeometry) 以获取特定的属性名称及其基于的属性值这个布尔条件。
我在这里寻找的是不添加这些布尔属性,有没有办法根据条件访问属性名称。我考虑过添加接口,但这里不可能,因为我有多个内部类,它们的属性需要包含在单个报告中。
谁能告诉我有没有其他方法可以做到这一点?
更新:
var columnResult = new OrderedDictionary();
GetReportHeaderColumnName(typeof(Space), columnResult);
public static void GetReportHeaderColumnName(Type type, OrderedDictionary headerNameByUnit)
{
var properties = type.GetProperties();
foreach (var propertyInfo in properties)
{
if (propertyInfo.PropertyType.IsClass && !propertyInfo.PropertyType.FullName.StartsWith("System."))
{
if (propertyInfo.PropertyType == typeof(Overridable<double>))
{
AddReportHeaderName(headerNameByUnit, propertyInfo);
}
else
{
GetReportHeaderColumnName(propertyInfo.PropertyType, headerNameByUnit);
}
}
else
{
AddReportHeaderName(headerNameByUnit, propertyInfo);
}
}
}
protected static void AddReportHeaderName(OrderedDictionary columnResult, PropertyInfo propertyInfo)
{
if (propertyInfo.GetCustomAttributes(typeof(DisplayNameWithUnitsAttribute), true).Any())
{
var displayNameWithUnitsAttribute = (DisplayNameWithUnitsAttribute)Attribute.GetCustomAttribute(propertyInfo, typeof(DisplayNameWithUnitsAttribute));
if (displayNameWithUnitsAttribute.IsIncludedInReport2)
{
columnResult.Add(displayNameWithUnitsAttribute.DisplayName, displayNameWithUnitsAttribute.Units);
}
}
}
【问题讨论】:
-
你能不能展示你到目前为止做了什么,有什么问题。添加任何属性很容易,但是在此之后您要做什么?你真的需要它们吗?
-
我不想使用这些布尔属性来访问属性名称,目前我正在使用这些。
-
@Serge,我更新了我的问题
-
听起来您在问我们如何在不使用属性的情况下指定要包含在报告中的列。那正确吗?如果是这样,我们需要了解用例。谁负责决定某个列是否包含在报告中?他们会喜欢如何表达他们的偏好?
-
@EnigmaState 这里的问题是您坚持通过说明系统应该不做什么来指定需求。最好通过说明系统应该做什么来指定需求。例如,如果最终用户可以通过在 Excel 工作簿的单元格中键入列名来指定列名,您可能会喜欢它。或者,也许您要求它们只能由开发人员配置。你需要缩小范围。说它不应该使用属性告诉我们很少。可能有一百种方法可以做到。
标签: c# .net .net-core reflection properties