RoL*_*LLs 4 c# reflection lambda properties json.net
我找到了一个帖子,对我遇到的问题有很好的答案,但我似乎找不到我正在寻找的小细节。
public class myModel
{
[JsonProperty(PropertyName = "id")]
public long ID { get; set; }
[JsonProperty(PropertyName = "some_string")]
public string SomeString {get; set;}
}
Run Code Online (Sandbox Code Playgroud)
我需要一个返回JsonProperty PropertyName特定属性的方法。也许我可以传递Type和Property我需要的东西,如果找到,该方法将返回该值。
这是我找到的方法,它使我朝着正确的方向(我相信)从这里获取
using System.Linq;
using System.Reflection;
using Newtonsoft.Json;
...
public static string GetFields(Type modelType)
{
return string.Join(",",
modelType.GetProperties()
.Select(p => p.GetCustomAttribute<JsonPropertyAttribute>()
.Where(jp => jp != null)
.Select(jp => jp.PropertyName));
}
Run Code Online (Sandbox Code Playgroud)
目标是调用这样的函数(任何修改都可以)
string field = GetField(myModel, myModel.ID);
Run Code Online (Sandbox Code Playgroud)
更新 #1
我修改了上面的这个,但我不知道如何获取IDfrom的字符串myModel.ID。
public static string GetFields(Type modelType, string field) {
return string.Join(",",
modelType.GetProperties()
.Where(p => p.Name == field)
.Select(p => p.GetCustomAttribute<JsonPropertyAttribute>())
.Where(jp => jp != null)
.Select(jp => jp.PropertyName)
);
}
Run Code Online (Sandbox Code Playgroud)
我想防止实际属性名称的硬编码字符串。例如,我不希望调用上面的方法为:
string field = GetField(myModel, "ID");
Run Code Online (Sandbox Code Playgroud)
我宁愿使用类似的东西
string field = GetField(myModel, myModel.ID.PropertyName);
Run Code Online (Sandbox Code Playgroud)
但我不完全确定如何正确地做到这一点。
谢谢!
这是一种在保持强类型的同时做到这一点的方法:
public static string GetPropertyAttribute<TType>(Expression<Func<TType, object>> property)
{
var memberExpression = property.Body as MemberExpression;
if(memberExpression == null)
throw new ArgumentException("Expression must be a property");
return memberExpression.Member
.GetCustomAttribute<JsonPropertyAttribute>()
.PropertyName;
}
Run Code Online (Sandbox Code Playgroud)
并这样称呼它:
var result = GetPropertyAttribute<myModel>(t => t.SomeString);
Run Code Online (Sandbox Code Playgroud)
你可以让它更通用一点,例如:
public static TAttribute GetPropertyAttribute<TType, TAttribute>(Expression<Func<TType, object>> property)
where TAttribute : Attribute
{
var memberExpression = property.Body as MemberExpression;
if(memberExpression == null)
throw new ArgumentException("Expression must be a property");
return memberExpression.Member
.GetCustomAttribute<TAttribute>();
}
Run Code Online (Sandbox Code Playgroud)
现在因为属性是通用的,你需要把PropertyName调用移到外面:
var attribute = GetPropertyAttribute<myModel, JsonPropertyAttribute>(t => t.SomeString);
var result = attribute.PropertyName;
Run Code Online (Sandbox Code Playgroud)