实例化和初始化代表

时间:2016-07-31 11:26:58

标签: c# delegates

我有一个关于代理编码的快速问题。

你为什么要

pf = t.Print;  //instantiate and initialize the delegate.

delegate void PrintFunction();

    public class Test
    {
        public void Print()
        {
            Console.WriteLine("Print 1 --instance");
        }

        public static void Print1()
        {
            Console.WriteLine("Print 2 -- static");
        }
    }
    class Program
    {
        static void Main(string[] args)
        {
            Test t = new Test();
            PrintFunction pf;
            pf = t.Print;  //instantiate and intialize the delegate

            pf += Test.Print1;
            pf += t.Print;


            if (null != pf)
            {
                pf();
            }
            else
                Console.WriteLine("delegate is empty");
        }
    }
}

4 个答案:

答案 0 :(得分:3)

委托是不可变的引用类型,它们的默认值为null。委托的默认构造函数接受与其签名匹配的方法。

所以你可以这样做:

Sub DebitCreditCrossMatch()

    Dim dictKeys As Object, dictRows As Object
    Dim DebitKey As String, CreditKey As String
    Dim arrDebit, arrCredit, items, keys
    Dim arrMatchRow(), arrMatchID()
    Dim ID As Long, rw As Long, x As Long, lastRow As Long

    lastRow = Cells(Rows.count, "A").End(xlUp).Row

    arrDebit = Range("A1", "A" & lastRow).Value
    arrCredit = Range("B1", "B" & lastRow).Value

    ReDim arrMatchID(lastRow - 2)
    ReDim arrMatchRow(lastRow - 2)

    Set dictKeys = CreateObject("Scripting.Dictionary")

    For x = 2 To lastRow

        DebitKey = arrDebit(x, 1) & ":" & arrCredit(x, 1)

        CreditKey = arrCredit(x, 1) & ":" & arrDebit(x, 1)

        If dictKeys.Exists(CreditKey) Then
            Set dictRows = dictKeys(CreditKey)
            items = dictRows.items
            keys = dictRows.keys
            rw = CLng(items(0))
            arrMatchRow(x - 2) = rw
            arrMatchRow(rw - 2) = x
            dictRows.Remove keys(0)

            If dictRows.count = 0 Then dictKeys.Remove CreditKey

        ElseIf dictKeys.Exists(DebitKey) Then
            Set dictRows = dictKeys(DebitKey)
            dictRows.Add x, x
        Else
            Set dictRows = CreateObject("Scripting.Dictionary")
            dictRows.Add x, x
            dictKeys.Add DebitKey, dictRows
        End If
    Next

    For x = 0 To lastRow - 2

        If Not IsEmpty(arrMatchRow(x)) And IsEmpty(arrMatchID(x)) Then
            rw = arrMatchRow(x) - 2
            arrMatchRow(rw) = x + 2
            ID = ID + 1
            arrMatchID(x) = ID
            arrMatchID(rw) = ID
        Else
            If IsEmpty(arrMatchRow(x)) Then
                arrMatchRow(x) = "No Match"
            End If
        End If

    Next

    Range("C2", "C" & lastRow).Value = WorksheetFunction.Transpose(arrMatchRow)
    Range("D2", "D" & lastRow).Value = WorksheetFunction.Transpose(arrMatchID)

    Set dictKeys = Nothing
    Set dictRows = Nothing

End Sub

或者:

var pf = new PrintFunction(Test.Print1);
pf += t.Print;

或者:

var pf = Test.Print1;
pf += t.Print;

编辑:

代表是参考类型的来源:MSDN

  

引用类型包含指向另一个内存位置的指针   保存数据。参考类型包括以下内容:

  • 字符串。
  • 所有数组,即使它们的元素是值类型
  • 类类型,例如Form
  • 代表

答案 1 :(得分:0)

您无需拨打代码pf = t.Print;。写pf = null;是完全可以接受的。

如果删除行pf = t.Print;,您只会发现编译器正在向您发送错误" CS0165使用未分配的本地变量' pf'"

这与编写代码没有什么不同:

bool flag;

if (flag)
{
}

它与代表无关。它只是一个编译器错误。

答案 2 :(得分:0)

所以你必须在调用它之前初始化委托,比如在调用类时。委托签名也必须与调用委托的方法相匹配。

感谢大家的帮助。 应该在我发布问题之前处理它。

再次感谢。

答案 3 :(得分:-1)

默认情况下,委托值为null,您应将其初始化为某些内容,然后使用它或添加其他方法。在您的样本中,将有2次称为t.Print,一次称为Test.Print1。

好的做法是将委托初始化为可空对象,然后使用它而不进行任何空检查,如下所示。

PrintFunction pf = () => {};
pf += Print1;
pf += Print;
pf += Print1;
pf();