Well, the dirty way could be to manually check for the signature of the method.
The signature verification method might look like this:
public static bool HasSameSignature(MethodInfo potentiallyHidingMethod, MethodInfo baseMethod) { //different name, therefore not same signature if (potentiallyHidingMethod.Name != baseMethod.Name) return false; //now we check if they have the same parameter types... var potentiallyHidingMethodParameters = potentiallyHidingMethod.GetParameters(); var baseMethodParameters = baseMethod.GetParameters(); //different number of parameters, therefore not same signature if (potentiallyHidingMethodParameters.Length != baseMethodParameters.Length) return false; for (int i = 0; i < potentiallyHidingMethodParameters.Length; i++) { //if a parameter type doesn't match, it not the same signature if (potentiallyHidingMethodParameters[i].ParameterType != baseMethodParameters[i].ParameterType) return false; } //if we've gotten this far, they have the same name and parameters, //therefore, it the same signature. return true; }
Then you need to check the methods of the derived interface to see if they hide (or match the signature) any methods of the base interface:
Type type = typeof(IInterfaceWithNewMethod); var potentiallyHidingMethods = type.GetMethods(); var baseTypeMethods =type.GetInterfaces() .SelectMany(@interface => @interface.GetMethods()); var hidingMethods = potentiallyHidingMethods .Where(hiding => baseTypeMethods.Any(baseMethod => HasSameSignature(hiding, baseMethod)));
Please note that this is a bit naive implementation. I would not be surprised if there is an easier way or corner cases that this does not cover.
EDIT: Slightly misunderstood the desired result. Using the code above, you will get all the methods of the base interface, as well as the derived methods of the interface, but filtered out any methods of the base interface that were hidden using the derived interface:
var allMethodsButFavouringHiding = potentiallyHidingMethods.Concat( baseTypeMethods.Where(baseMethod => !potentiallyHidingMethods.Any(potentiallyhiding => HasSameSignature(potentiallyhiding, baseMethod))));
EDITx2: I checked the following interfaces:
public interface IBaseInterface { string BaseMethodTokeep(); string MethodToHide(); string MethodSameName(); } public interface IInterfaceWithNewMethod : IBaseInterface { new string MethodToHide(); new string MethodSameName(object butDifferentParameters); string DerivedMethodToKeep(); }
The result is a MethodInfo collection:
MethodToHide (IInterfaceWithNewMethod) MethodSameName (IInterfaceWithNewMethod) DerivedMethodToKeep (IInterfaceWithNewMethod) BaseMethodTokeep (IBaseInterface) MethodSameName (IBaseInterface)
Thus, it saves any methods of the base interface that are not hidden, any derived interface methods (which are hidden or otherwise), and honors any changes to the signature (that is, various parameters that will not lead to hiding).
EDITx3: another test with overloads added:
public interface IBaseInterface { string MethodOverloadTest(); string MethodOverloadTest(object withParam); } public interface IInterfaceWithNewMethod : IBaseInterface { new string MethodOverloadTest(); }
With the results:
MethodOverloadTest() for IInterfaceWithNewMethod MethodOverloadTest(object) for IBaseInterface