user_defined_function
user_defined_function

Reputation: 33

Access modifiers related to interface

I am confused over the below paragraph found in https://learn.microsoft.com/en-us/dotnet/csharp/programming-guide/classes-and-structs/access-modifiers

Normally, the accessibility of a member isn't greater than the accessibility of the type that contains it. However, a public member of an internal class might be accessible from outside the assembly if the member implements interface methods or overrides virtual methods that are defined in a public base class.

Could anyone help to give an example of the last sentence? If the class is internal, then no instance of the class can be created outside the assembly. How is it possible that one can access a member of such class from outside the assembly, even if the member is declared public?

Thanks

Upvotes: 1

Views: 184

Answers (2)

StriplingWarrior
StriplingWarrior

Reputation: 156504

If the class is internal, then no instance of the class can be created outside the assembly.

Actually, the class could be created outside the assembly using reflection.

More commonly, it's possible that the class could be created inside the assembly and then passed to methods outside the assembly, but simply cast as an interface or parent class which is publicly visible.

For an example, consider the following C# expression:

((Expression<Func<int, bool>>) (i => i == 0))

The Body property of this expression is cast as an Expression, but the actual type of that particular Expression is a LogicalBinaryExpression, which is a class that's internal to the System.Core library.

    internal sealed class LogicalBinaryExpression : BinaryExpression {
        private readonly ExpressionType _nodeType;
 
        internal LogicalBinaryExpression(ExpressionType nodeType, Expression left, Expression right)
            : base(left, right) {
            _nodeType = nodeType;
        }
 
        public sealed override Type Type {
            get { return typeof(bool); }
        }
 
        public sealed override ExpressionType NodeType {
            get { return _nodeType; }
        }
    }

Notice how the public Type and NodeType properties are overridden by this type. So even though this type is internal and you can never cast it to a LogicalBinaryExpression in your own code, it still has public members which you can access via the Expression type.

Console.WriteLine(((Expression<Func<int, bool>>) (i => i == 0)).Body.Type.ToString());
// Output: System.Boolean

Upvotes: 3

ProgrammingLlama
ProgrammingLlama

Reputation: 38757

Imagine you create the following service and interface:

public interface IFoo
{
    void Bar();
}

internal class ConcreteFoo : IFoo
{
    public void Bar()
    {
        Console.WriteLine("Hello from my concrete foo!");
    }
}

You then expose a factory:

public class Factory
{
    public IFoo CreateFoo()
    {
        return new ConcreteFoo();
    }
}

The Bar method is implementing the interface requirement of void Bar(); in IFoo. While consumers can't instantiate a ConcreteFoo, it's possible for other entities within your library to create and return a ConcreteFoo boxed as an IFoo (which is public), thereby allowing access to the member in the consuming code.

Upvotes: 4

Related Questions