delegate 转变成 Func 该怎样实现?

qq_24859323 2016-09-14 12:10:32

namespace JDD_Logic.Sys
{
public delegate string JsonHandler(object obj);
public class JsonService
{
public string SendJson_SQL(object obj)
{
return JsonConvert.SerializeObject(obj);
}

public string SendJson_Ora(object obj)
{
return Convert8859P1ToGB2312(JsonConvert.SerializeObject(obj));
}

public string Convert8859P1ToGB2312(string s)
{
return System.Text.Encoding.Default.GetString(System.Text.Encoding.GetEncoding("iso-8859-1").GetBytes(s));
}
}
}


FatherHandler.ashx(公共方法类)调用
        public void RedisCache1(HttpContext context, Type t, string mth, string key, Type[] ts, object[] o,JsonHandler handler)
{
string json = String.Empty;
if (RedisBase.Item_Exist(key))//判断Redis中,key是否存在;若存在,直接从redis取值,不存在则执行数据库访问方法,这种机制减缓了数据库的压力,提升了系统性能.
{
json = RedisBase.GetValue(key);//根据key获取value
}
else
{
object className = Activator.CreateInstance(t);//反射方法
MethodInfo mInfo = null;
object obj = null;
if (ts != null && o != null)//执行带有多种参数的方法
{
mInfo = t.GetMethod(mth, ts);
obj = mInfo.Invoke(className, o);
}
else//执行无参数的方法
{
mInfo = t.GetMethod(mth);
obj = mInfo.Invoke(className, null);
}
json = handler(obj);
RedisBase.Item_Set<string>(key, json, 120);//根据key设置value
}
context.Response.Write(json);
context.Response.End();
}

控制器调用(ashx)

public void ShopInfo(HttpContext context)
{
//fth.RedisCache(context, d.GetType(), "GetShop", "ShopInfo", FatherHandler.DataBaseType.SQL_Server);
//fth.RedisCacheForMsSql(context, d.GetType(), "GetShop", "ShopInfo",null,null);
JDD_Logic.Sys.JsonService j=new JDD_Logic.Sys.JsonService();
fth.RedisCache1(context, d.GetType(), "GetShop", "ShopInfo", null, null, j.SendJson_SQL);
}


我现在想把delegate转换成Func,因为前者涉及到拆箱,损失性能,想用Func实现 不知道该怎样编码,求大牛指点一二。。。
...全文
247 4 打赏 收藏 转发到动态 举报
写回复
用AI写文章
4 条回复
切换为时间正序
请发表友善的回复…
发表回复
  • 打赏
  • 举报
回复
上面的道理如果明白的话,回到你的问题就会发现,你最初的想法其实无法实现。因为你无法保证上面代码中的 target 是唯一不变的对象实例。 通用的框架,应该按照接口来进行强类型地设计。例如
cmd = (ICommandABC)Activator.CreateInstance(cmdType);
cmd.SetParameters(a,b,c,d);
var result = cmd.Execute();
这里,反射了一个 ICommandABC 实例,然后调用这个接口定义的两个方法。你可以看到,这就不会去考虑什么“想用 Func 泛型实现”的问题,根本不必考虑委托抽象,应该直接用最终业务领域接口来操作。
  • 打赏
  • 举报
回复
要想提高性能,你的 JsonHandler 和 RedisCache1 的声明上就不应该出现 object 类型声明,而应该用泛型。 有些所谓的“框架”是滥用反射的。这些框假不但调试困难,而且还不能保证在编译期检查编程结果中的类型错误(程序在运行中跑了几百遍之后才在某个特定的数据状态下在用户面前崩溃),这就是不好的框架。这些框假可能用雷人的时髦名词儿来吸引编程“小白粉”,然后这样的框架只应该当作“学习”而不应该滥用。 程序中使用反射应该非常节省,尽可能仅用一次反射,以后相关的输出都是强类型的代码。因此在程序框架设计中应该杜绝滥用 object 类型声明的做法,仅仅在你的框架代码的“最外层”自己几乎控制不了的地方才用一次反射。
  • 打赏
  • 举报
回复
只要你在最外层“最高层”的设计上滥用 object 类型声明,那么就一定有这个问题。所以不是说底层改变,而是应该从方法接口上就改变。例如应该使用泛型,而决不写 object 类型声明。或者如果是直接就是具体的、写死的自定义对象类型。 假设要转换为 Func<ABC>,可以这样写
var  func =(Func<ABC>) method.CreateDelegate(typeof(Func<ABC>), target);
ABC result = func();
但是如果仅仅调用一次 func 就释放了,那么这个做法显然是得不偿失的。如果你将 Delegate 在进程中缓存起来,成千上万次地复用,那么才能显出 Delegate 调用比 MethodInfo.Invoke 性能更好的特点。
qq_24859323 2016-09-14
  • 打赏
  • 举报
回复
引用 1 楼 sp1234 的回复:
只要你在最外层“最高层”的设计上滥用 object 类型声明,那么就一定有这个问题。所以不是说底层改变,而是应该从方法接口上就改变。例如应该使用泛型,而决不写 object 类型声明。或者如果是直接就是具体的、写死的自定义对象类型。 假设要转换为 Func<ABC>,可以这样写
var  func =(Func<ABC>) method.CreateDelegate(typeof(Func<ABC>), target);
ABC result = func();
但是如果仅仅调用一次 func 就释放了,那么这个做法显然是得不偿失的。如果你将 Delegate 在进程中缓存起来,成千上万次地复用,那么才能显出 Delegate 调用比 MethodInfo.Invoke 性能更好的特点。
我如果写成

public delegate string JsonHandler<T>(T t);
        public string SendJson_SQL<T>(T t)
        {
            return JsonConvert.SerializeObject(t);
        }
 
        public string SendJson_Ora<T>(T t)
        {
            return Convert8859P1ToGB2312(JsonConvert.SerializeObject(t));
        }
在调用委托的时候,还需要指明类型object,这样是不是就没意义了?

62,272

社区成员

发帖
与我相关
我的任务
社区描述
.NET技术交流专区
javascript云原生 企业社区
社区管理员
  • ASP.NET
  • .Net开发者社区
  • R小R
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

.NET 社区是一个围绕开源 .NET 的开放、热情、创新、包容的技术社区。社区致力于为广大 .NET 爱好者提供一个良好的知识共享、协同互助的 .NET 技术交流环境。我们尊重不同意见,支持健康理性的辩论和互动,反对歧视和攻击。

希望和大家一起共同营造一个活跃、友好的社区氛围。

试试用AI创作助手写篇文章吧