C# 查找类型上立即实现的接口
在以下场景中调用typeof(Bar).GetInterfaces()时,该方法返回IFoo和IBarC# 查找类型上立即实现的接口,c#,reflection,C#,Reflection,在以下场景中调用typeof(Bar).GetInterfaces()时,该方法返回IFoo和IBar 接口IFoo{} 接口IBar:IFoo{} 类栏:IBar{} 有没有一种方法可以让我在工具栏上只找到即时接口(IBar) 不,编译代码中没有“立即”接口。您的类有效地编译为: class Bar : IBar, IFoo { } 你无法区分两者。您唯一能做的就是检查所有这些接口,看看是否有两个或多个接口相互继承(即使在这种情况下,您也无法真正检查类的作者是否在代码中明确提到了基接口)
接口IFoo{}
接口IBar:IFoo{}
类栏:IBar{}
有没有一种方法可以让我在工具栏上只找到即时接口(IBar) 不,编译代码中没有“立即”接口。您的类有效地编译为:
class Bar : IBar, IFoo { }
你无法区分两者。您唯一能做的就是检查所有这些接口,看看是否有两个或多个接口相互继承(即使在这种情况下,您也无法真正检查类的作者是否在代码中明确提到了基接口):
静态IEnumerable GetImmediateInterface(类型)
{
var interfaces=type.GetInterfaces();
var结果=新哈希集(接口);
foreach(接口中的i型)
result.ExceptWith(i.GetInterfaces());
返回结果;
}
公共接口IRoo{}
公共接口ISoo:IRoo{}
公共接口IMoo:ISoo{}
公共接口IGoo:IMoo{}
公共接口IFoo:IGoo{}
公共接口IBar:IFoo{}
公共类栏:IBar{}
私有无效按钮1\u单击(对象发送者,事件参数e){
Type[]interfaces=typeof(Bar).GetInterfaces();
输入immediateInterface=GetPrimaryInterface(接口);
//伊巴尔
}
公共类型GetPrimaryInterface(类型[]接口)
{
if(interfaces.Length==0)返回null;
if(interfaces.Length==1)返回接口[0];
字典类型分数=新字典();
foreach(接口中的t型)
加上(t,0);
foreach(接口中的t型)
foreach(接口中的t1类型)
if(t.IsAssignableFrom(t1))
打字分数[t1]++;
类型winner=null;
int最佳分数=-1;
foreach(typeScores中的KeyValuePair对){
如果(pair.Value>bestScore){
最佳分数=配对值;
获胜者=配对。密钥;
}
}
返回赢家;
}
这将选择具有最长继承树的接口
typeof(Bar)
.GetInterfaces()
.OrderByDescending(i => i.GetInterfaces().Length)
.FirstOrDefault()
这对于我的用例来说已经足够了。为什么要这样做?在我看来,这似乎是代码中的一个设计缺陷;)返回的数组是不确定的。@Oliver,系统将接口映射到具体类型。问题是另一种类型可能正在实现IFoo,但我们不想将IFoo接口与Bar类相关联,而是与IBar接口相关联。这是您自己的系统吗?如果是这样,您是否考虑过实现一种用于接口类关联的注册表?您还可以对配置方法进行一些约定,其中接口和类名必须遵循rule=“I”+。尽管如此,我仍然认为存在设计缺陷,因为类栏不仅是一个IBar,而且是一个IFoo。好问题。我在另一个线程上发现了。看起来很有趣的代码,但是为什么
GetPrimaryInterface
只返回一种接口类型?似乎需要潜在地返回多个接口类型才有用。
public interface IRoo { }
public interface ISoo : IRoo { }
public interface IMoo : ISoo { }
public interface IGoo : IMoo { }
public interface IFoo : IGoo { }
public interface IBar : IFoo { }
public class Bar : IBar { }
private void button1_Click(object sender, EventArgs e) {
Type[] interfaces = typeof(Bar).GetInterfaces();
Type immediateInterface = GetPrimaryInterface(interfaces);
// IBar
}
public Type GetPrimaryInterface(Type[] interfaces)
{
if (interfaces.Length == 0) return null;
if (interfaces.Length == 1) return interfaces[0];
Dictionary<Type, int> typeScores = new Dictionary<Type, int>();
foreach (Type t in interfaces)
typeScores.Add(t, 0);
foreach (Type t in interfaces)
foreach (Type t1 in interfaces)
if (t.IsAssignableFrom(t1))
typeScores[t1]++;
Type winner = null;
int bestScore = -1;
foreach (KeyValuePair<Type, int> pair in typeScores) {
if (pair.Value > bestScore) {
bestScore = pair.Value;
winner = pair.Key;
}
}
return winner;
}
typeof(Bar)
.GetInterfaces()
.OrderByDescending(i => i.GetInterfaces().Length)
.FirstOrDefault()