how to use anonymous generic delegate in C# 2.0

748 Views Asked by At

I have a class called NTree:

class NTree<T>
{

    delegate bool TreeVisitor<T>(T nodeData);

    public NTree(T data)
    {
        this.data = data;
        children = new List<NTree<T>>();
        _stopTraverse = false;
    }

        ...

    public void Traverse(NTree<T> node, TreeVisitor<T> visitor)
    {
        try
        {
            _stopTraverse = false;
            TraverseInternal(node, visitor);
        }
        finally
        {
            _stopTraverse = false;
        }
    }

    private void TraverseInternal(NTree<T> node, TreeVisitor<T> visitor)
    {
        if (_stopTraverse)
            return;

        if (!visitor(node.data))
        {
            _stopTraverse = true;
        }
        foreach (NTree<T> kid in node.children)
            TraverseInternal(kid, visitor);
    }

When I try to use Traverse with anonymous delegate I get:

Argument '2': cannot convert from 'anonymous method' to 'NisConverter.TreeVisitor'

The code:

tTable srcTable = new tTable();
DataRow[] rows;
rootTree.Traverse(rootTree, delegate(TableRows tr)
    {
        if (tr.TableName == srcTable.mappingname)
        {
            rows = tr.Rows;
            return false;
        }
    });

This however produces no errors:

    static bool TableFinder<TableRows>(TableRows tr)
    {
        return true;
    }

...

rootTree.Traverse(rootTree, TableFinder);

I have tried to put "arrowhead-parenthisis" and everything to anonymous delegate but it just does not work. Please help me!

Thanks & BR -Matti

2

There are 2 best solutions below

2
On BEST ANSWER

The anonymous delegate you posted lacks the return of a boolean value (most probably the value true when the if(...) guard is false. Thus, it signature is actually void (TableRow) instead of bool (TableRow), and the compiler is unable to make the conversion.

So the syntax should be:

tTable srcTable = new tTable();  DataRow[] rows;  rootTree.Traverse(rootTree, delegate(TableRows tr) 
    { 
        if (tr.TableName == srcTable.mappingname) 
        { 
            rows = tr.Rows; 
            return false; 
        } 
        return true;
    });
2
On

The declaration of TreeVisitor is wrong: it introduces a new type parameter (which conflicts with the declaration of NTree). Just remove the template stuff and you get:

delegate bool TreeVisitor(T nodeData);

Then you can have:

class X
{

    void T()
    {
        NTree<int> nti = new NTree<int>(2);

        nti.Traverse(nti, delegate(int i) { return i > 4; });

    }
}