在C#中为函数名创建别名

时间:2011-05-22 14:32:28

标签: c# alias

我想在C#中为函数名创建一个别名。

除了函数重载有什么办法吗?

public class Test
{
    public void A()
    {
        ...
    }
}

我想在下面打电话给B替换。

var test = new Test();
test.B();

8 个答案:

答案 0 :(得分:24)

我很惊讶没人提到代表。它可能与C#中的方法别名一样接近:

class DelegaTest
{
    public string F()
    {
        return null;
    }

    public string F(int arg)
    {
        return arg.ToString();
    }

    public void G(int arg1, int arg2)
    {
    }

    /// <summary>
    /// Delegate for `string F()`
    /// </summary>
    public Func<string> D1 => F;

    /// <summary>
    /// Delegate for `string F(int arg)`
    /// </summary>
    public Func<int, string> D2 => F;

    /// <summary>
    /// Delegate for `void G(int arg1, int arg2)`
    /// </summary>
    public Action<int, int> E => G;
}

答案 1 :(得分:12)

您可以使用extension method

public static class Extensions 
{
    public static void B(this Test t)
    {
       t.A();
    }
}

但它不是别名。这是一个包装。


修改
ps:我同意你的问题的评论者,如果我们知道你真正想做什么,如果我们理解你想要解决的问题,我们就能给出更好的答案。

我真的没有看到产生上述扩展方法的重点。

答案 2 :(得分:5)

实际上,函数别名更多是C#术语中的 delegates (就像C ++中的函数指针一样)。这是一个:

public class Test
{
    public void Test()
    {
        B += A;
    }

    public void A()
    {
        ...
    }

    public Action B;
}

但你必须将其称为B.Invoke(),因为它是无参数的。如果它有一个或多个参数,这不会有问题。

答案 3 :(得分:4)

这已经很老了,但我对为什么一个人可能想要别名一个方法名称有一个回应。它一直在发生。因为某些开发人员给了一个方法一个没有任何意义的名称,或者它根本没有准确地描述该方法的目的。在旧的,经过良好调整的解决方案中,该方法被多次调用。因此,执行大型重构和重新测试是因为命名不合理的方法无法证明,只需给它一个有意义的别名。这样,新代码将来会正确阅读。

即。保存网格控件,并且方法名称为IsReferenceSelectedSendEmail。该名称暗示该方法将识别用户在网格中选择的引用是否是SendEmail。该方法真正做的是迭代所有引用,并确定它们中的任何一个是否是SendEmail。

简单的解决方案。将该方法别名为AnyReferenceIsSendEmail,以便将来的代码正确读取:if(AnyReferenceIsSendEmail())...

现在,如果我们可以获得关键字“除非”否定if条件。

IMO

答案 4 :(得分:1)

C#是面向对象的语言,因此您无法创建“函数别名”。你只能操纵类。正如前面提到的,你可以用扩展方法扩展类,你也可以创建派生类并在其中创建新方法,这将调用派生方法:

    class Test
    {
        public void A()
        {
            MessageBox.Show("Function A");
        }
    }

    class Test2: Test
    {
        public void B()
        {
            A();
        }
    }

但是,如果您希望在初始课程B()上致电Test,那么您只有一种方法 - 创建扩展方法。

答案 5 :(得分:1)

这很有效。

class Program
{
    delegate void B();
    static Test t = new Test();
    static B b = t.A;

    static void Main(string[] args)
    {
        b();
    }

}

class Test
{
    public void A()
    {
    }
}

答案 6 :(得分:0)

这篇文章中有一些评论,说明为什么有人要这样做。我目前正在为一个图形项目实现Vector类型,并且我正在使用的需求文档可互换地引用Vector的大小/长度。为了提高效率,我宁愿不将Magnitude()方法包装在Length()方法内部,但是如果该结构同时理解这两个术语,那么为了便于阅读,这似乎是不错的选择。

克里斯蒂安·达文(ChristianDavén)提到的委托方法可能是执行此操作最有效的方法,但我可能最好将其添加到方法块中:

/// <summary>
/// Calculate the magnitude / length of a vector, including the W component.
/// </summary>
/// <remarks>
/// This calculation will break down if you try to take the magnitude of a point.
/// </remarks>
/// <returns>The magnitude / length of the vector.</returns>
public float Magnitude()
{
    return (float)Math.Sqrt(X * X + Y * Y + Z * Z + W * W);
}

答案 7 :(得分:0)

我知道这很老了,但是我确实认为这是一个相关的问题,可以使用C#3.0中可用的委托/ Lambda表达式很容易地解决,如果内存正确,那是在OP时代。

让我们想象一下,我们正在创建一个游戏,要求我们实时登录xbox并有两个按钮-一个用于登录,另一个用于切换用户。名为SignIn的单个函数将同时处理它们,但这在添加onclick处理程序时会导致可读性差。

幸运的是,可以使用委托和Lambda表达式轻松解决此问题。

具有SignIn函数:

public static async void SignIn(object coreDispatcher)
{
...
}

以下是创建“别名”的Lambda表达式

public static async void SwitchUser(object param) => SignIn(param);

现在我可以调用SignInSwitchUser并使用相同的代码,但提供更有意义的代码