我有一个包含这些条目的(sql)表:
表:
Type (varchar) Json (varchar)
MyClassA { "Id": 1, "Name": "OneName" }
MyClassB { "Id": 2, "Name": "TwoName" }
我需要调用ClassA和/或ClassB中的方法来更改Name属性。
类似下一个代码:
public void Test(string type, string json)
{
Type type = Type.GetType($"MyNamespace.a.b.{type}, MyDll");
// Some code here....
// - Casting to IData ??
// - var obj = JsonConvert.DeserializeObject(json); ??
// - var obj = JsonConectt.DeserializeObject<type>(json) ??
// - var x = Convert.Change(...) ??
instance.DoSomething("bazinga");
}
public interface IData
{
void DoSomething();
}
public class MyClassA : IData
{
public int Id {get; set;}
public string Name {get; set;}
public void DoSomething(string newName)
{
Name = newName;
}
}
public class MyClassB : IData
{
public int Id {get; set;}
public string Name {get; set;}
public void DoSomething(string newName)
{
name = $"{Id}, {newName}";
}
}
尝试A:
var obj = JsonConvert.DeserializeObject(json);
var ins = obj as IData;
// ins = null
尝试B:
dynamic obj = JsonConvert.DeserializeObject<dynamic>(json);
// failed
尝试C:
var obj = JsonConvert.DeseriallizeObject<type>(json);
// Not allowed to use 'type' in this way.
答案 0 :(得分:2)
您可以执行以下操作:
var instance = JsonConvert.DeserializeObject(json, type) as IData;
有关官方文档,请参阅HERE。第二个参数将定义要反序列化的类型。
答案 1 :(得分:0)
因此,首先,您必须为每个通用调用创建一个专用类型,通常在运行时完成。你需要做的就是自己创建这种类型是使用一些反思:
public void Test(string type, string json)
{
Type type = Type.GetType($"MyNamespace.a.b.{type}, MyDll");
// from all method named "DeserializeObject"
// find the one that is generic method
MethodInfo deserializeObjectMethodInfo = typeof(JsonConvert)
.GetMethods(BindingFlags.Static | BindingFlags.Public)
.FirstOrDefault(m => m.IsGenericMethod && m.Name == "DeserializeObject");
// create a specialized method for the requested type
// same as you would call DeserializeObject<type>
MethodInfo specializedDeserializeObject = deserializeObjectMethodInfo.MakeGenericMethod(type);
// invoke that method with json as parameter
// and cast it to IData
IData data = (IData)specializedDeserializeObject.Invoke(null, json);
// do whatever you want with the deserialized object
data.DoSomething("bazinga");
}