明确实现的方法具有什么可访问性?

时间:2019-07-03 15:02:17

标签: c# interface

所以我的朋友说,显式实现的接口方法是私有的。

请考虑以下示例作为参数:

interface ITest
{
    void Test();
}

class Test : ITest
{
    // IS THIS METHOD PRIVATE?
    void ITest.Test()
    {
        Console.WriteLine("What am I?");
    }
}

我不相信这一点,我将在两边列出论点:

他:

我:

  • 除非您将自己转换为Test,否则您不能从类内部访问ITest方法(这是显式实现的方法的工作方式,但您不能从类内部调用该方法)如果它确实是该类中的私有方法?)
  • 当您将Test实例强制转换为ITest时,Test方法将公开可用,并且可以在任何地方调用,因此不能私有。
  • 我不知道这有多可靠,但是在this answer中声明“明确实现的接口成员”是公开的。

我认为我们都知道显式接口实现的工作原理和用法,但是在这里我们不确定谁是正确的。
问题真的可以归结为:

您可以将Test类中的Test方法称为“私有方法”吗?

1 个答案:

答案 0 :(得分:3)

显式接口方法具有private访问级别。

让我们看看(借助 Reflection 的帮助):

  using System.Reflection;

 ...

  var result = typeof(Test)
    .GetMethods(BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance)
    .Select(info => $"{(info.IsPrivate ? "private" : "not private")} {info.Name}");

  string report = string.Join(Environment.NewLine, result);

  Consolw.Write(report);

结果:

private WFA_Junk_4.Form1.ITest.Test // <- Method of interest
not private Equals
not private GetHashCode
not private Finalize
not private GetType
not private MemberwiseClone
not private ToString  

所以我们不能明确执行它们:

Test test = new Test();

// ITest.Test() call which is OK
(test as ITest).Test();

// Doesn't compile: 
//   1. Private method
//   2. Wrong name; should be typeof(ITest).FullName.Test() which is not allowed 
test.Test(); 

由于我们不能按原样放置方法名称,因此,我看到直接调用ITest.Test的唯一方法是反射:

class Test : ITest {
  ...
  public void SomeMethod() 
  {
     // we can't put method's name as it is `SomeNamespace.ITest.Test`
     // Let's find it and execute
     var method = this
       .GetType()
       .GetMethod($"{(typeof(ITest)).FullName}.Test", 
                    BindingFlags.Instance | BindingFlags.NonPublic);

     method.Invoke(this, new object[0]);
  }