C#委托匿名函数闭包等

1、Delegate普通委托:

  • 如public delegate void MyDelegate();
    public MyDelegate mydelegate; //需要实例化的,用的时候直接=赋值就可以了

2、事件:利用event声明,相对于普通的委托,拥有了2条限制

  • 1)此委托无法被其他类直接调用
  • 2)此委托无法通过=直接赋值,只能通过+=(订阅)和-=(取消订阅)方式赋值

3、Action和Func可以声明委托,并无需实例化

  • 需要using System;
  • public event Action myDelegate; //声明无返回值,无参数
  • public event Action<T1, T2> myDelegate; //声明无返回值,有参数
  • Func<int> myDelegate; //声明无返回值,int型参数
  • Func<int, string, bool> myDelegate; //声明返回bool,int, string型参数

4、定义 public event EventHandler<AttackEventArgs> OnAttack;

//需要创建参数类等
    public class AttackEventArgs : EventArgs
    {
        public Vector3 startPos;
        public Vector3 endPos;
    }
//调用委托
  if(Input.GetMouseButton(0))
  {
  // ?.将会先判OnAttack是否为null
  // invoke还没查
    OnAttack?.Invoke(this, new AttackEventArgs{
    startPos = transform.position,
    endPos = Camera.main.ScreenToWorldPoint(Input.mousePosition)
     });
  }
//委托订阅
    void Start()
    {
        playAttack.OnAttack += PlayerOrdinary;
    }
  //感觉和普通事件委托没啥区别。就是感觉是可以传一批数据,而且可以调用参数类的一些方法
    private void PlayerOrdinary(object sender, PlayerAttack.AttackEventArgs e)
    {
        Debug.DrawLine(e.startPos, e.endPos);
        // var newBullet = Instantiate(bullet, transform.position, Quaternion.identity);
        Vector3 direction = (e.startPos - e.endPos).normalized;
        
    }

闭包

Action[] actions = new Action[5];
    for (var i = 0; i < actions.Length; i++) {
        actions[i] = () => { Debug.Log(i); };
    }
 
    foreach (var item in actions) {
        item();
    }
这一段代码执行完结果为5,5,5,5,5
为什么?
闭包可以使其访问到其访问不到的变量。也就说其访问到了i,i在循环完后i=5;然后这5个委托都引用了这个i。所以打印的都是i

下一段代码

Action[] actions = new Action[5];
    for (var i = 0; i < actions.Length; i++) {
        int a = i; //栈中分配一个空间 值为 i的值
        actions[i] = () => { Debug.Log(a); };
    }
 
    foreach (var item in actions) {
        item();
    }
这里打印出的是0,1,2,3,4。这5个分别引用了a。然后每次都给a进行了一次赋值

正常情况下,上面函数中变量在随着函数运行将会被释放除了那个数组。然而在闭包会造成C#为其生成一个类用于存储这些被引用的外部变量。因为类是引用类型所以会造成内存分配。

注意:要明确一点C# Lambda表达式使用局部变量是按引用传递的,E.g. 上面的打印全是5的原因


闭包造成的内存泄露

http://www.360doc.com/content/19/0402/14/22877383_825931106.shtml


  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值