Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

What are the equivalents of C#'s access modifiers in Java and Scala?

Having previously worked in C#, I now spend a lot of time working in Scala and Java. This can be confusing, because the three languages use similar names for their access modifiers but don't always mean the same thing.

What are the equivalents of C#'s access modifiers in Java and Scala?

like image 551
Tim Goodman Avatar asked Apr 09 '14 16:04

Tim Goodman


1 Answers

Here are the closest equivalents to C#'s access modifiers within Java and Scala. In the case of internal (accessible within the same assembly), there is no exact equivalent. In Java you can limit accessibility to the same package, but packages are more directly equivalent to C#'s namespaces than they are to assemblies.

("no modifier" in the following table is interpreted as applying to class members. That is, in C# class members with no modifier are private. This is not true of top-level types, which default to internal.)

 ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
| C#                  | Java            | Scala                    | Meaning                                                                                                       |
|----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
| no modifier         | private (1)     | private                  | accessible only within the class where it is defined                                                          |
| private             |                 |                          |                                                                                                               |
|----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
| protected           |   --            | protected                | accessible within the class and within derived classes (2)                                                    |
|----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
| internal            | no modifier     | private[package_name]    | accessible within the same assembly (C#) or within the same package (Java / Scala) (3)                        |
| ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
| protected internal  | protected       | protected[package_name]  | accessible within derived classes (2) and anywhere in the same assembly (C#) or package (Java / Scala) (3)    |
|----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
| public              | public          | no modifier              | accessible anywhere                                                                                           |
 ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

(1) In Java, private members of an inner class are visible to the outer class, but that's not true in C# or Scala. In Scala, you can say private[X] where X is the outer class to get the Java behavior.

(2) In C# and Scala, a protected member is visible within a class if it's a member of an instance of that class or a further derived class, but not if it's a member of an instance of a less-derived class. (The same is true in Java, except where it's accessible due to being in the same package.)

Example (in C#):

class Base
{
    protected void Foo() {}

    void Test()
    {
        Foo(); // legal
        this.Foo(); // legal

        new Base().Foo(); // legal
        new Derived().Foo(); // legal
        new MoreDerived().Foo(); // legal
    }
}

class Derived : Base
{
    void Test1()
    {
        Foo(); // legal
        this.Foo(); // legal

        new Base().Foo(); // illegal !
        new Derived().Foo(); // legal
        new MoreDerived().Foo(); // legal
    }
}

class MoreDerived : Derived
{
    void Test2()
    {
        Foo(); // legal
        this.Foo(); // legal

        new Base().Foo(); // illegal !
        new Derived().Foo(); // illegal !
        new MoreDerived().Foo(); // legal
    }
}

(3) In Scala, you can get the Java behavior by specifying the inner-most package, but you can also specify any enclosing package.

like image 61
Tim Goodman Avatar answered Oct 19 '22 03:10

Tim Goodman