Related
In Java, are there clear rules on when to use each of access modifiers, namely the default (package private), public, protected and private, while making class and interface and dealing with inheritance?
The official tutorial may be of some use to you.
Class
Package
Subclass(same pkg)
Subclass(diff pkg)
World
public
+
+
+
+
+
protected
+
+
+
+
no modifier
+
+
+
private
+
+ : accessible
blank : not accessible
(Caveat: I am not a Java programmer, I am a Perl programmer. Perl has no formal protections which is perhaps why I understand the problem so well :) )
Private
Like you'd think, only the class in which it is declared can see it.
Package Private
It can only be seen and used by the package in which it was declared. This is the default in Java (which some see as a mistake).
Protected
Package Private + can be seen by subclasses or package members.
Public
Everyone can see it.
Published
Visible outside the code I control. (While not Java syntax, it is important for this discussion).
C++ defines an additional level called "friend" and the less you know about that the better.
When should you use what? The whole idea is encapsulation to hide information. As much as possible you want to hide the detail of how something is done from your users. Why? Because then you can change them later and not break anybody's code. This lets you optimize, refactor, redesign, and fix bugs without worrying that someone was using that code you just overhauled.
So, the rule of thumb is to make things only as visible as they have to be. Start with private and only add more visibility as needed. Only make public that which is necessary for the user to know, every detail you make public cramps your ability to redesign the system.
If you want users to be able to customize behaviors, rather than making internals public so they can override them, it's often a better idea to shove those guts into an object and make that interface public. That way they can simply plug in a new object. For example, if you were writing a CD player and wanted the "go find info about this CD" bit customizable, rather than make those methods public you'd put all that functionality into its object and make just your object getter/setter public. In this way being stingy about exposing your guts encourages good composition and separation of concerns
I stick with just "private" and "public". Many OO languages just have that. "Protected" can be handy, but it's a cheat. Once an interface is more than private it's outside of your control and you have to go looking in other people's code to find uses.
This is where the idea of "published" comes in. Changing an interface (refactoring it) requires that you find all the code which is using it and change that, too. If the interface is private, well no problem. If it's protected you have to go find all your subclasses. If it's public you have to go find all the code which uses your code. Sometimes this is possible, for example, if you're working on corporate code that's for internal use only it doesn't matter if an interface is public. You can grab all the code out of the corporate repository. But if an interface is "published", if there is code using it outside your control, then you're hosed. You must support that interface or risk breaking code. Even protected interfaces can be considered published (which is why I don't bother with protected).
Many languages find the hierarchical nature of public/protected/private to be too limiting and not in line with reality. To that end, there is the concept of a trait class, but that's another show.
Here's a better version of the table, that also includes a column for modules.
Explanations
A private member (i) is only accessible within the same class as it is declared.
A member with no access modifier (j) is only accessible within classes in the same package.
A protected member (k) is accessible within all classes in the same package and within subclasses in other packages.
A public member (l) is accessible to all classes (unless it resides in a module that does not export the package it is declared in).
Which modifier to choose?
Access modifiers is a tool to help you to prevent accidentally breaking encapsulation(*). Ask yourself if you intend the member to be something that's internal to the class, package, class hierarchy or not internal at all, and choose access level accordingly.
Examples:
A field long internalCounter should probably be private since it's mutable and an implementation detail.
A class that should only be instantiated in a factory class (in the same package) should have a package restricted constructor, since it shouldn't be possible to call it directly from outside the package.
An internal void beforeRender() method called right before rendering and used as a hook in subclasses should be protected.
A void saveGame(File dst) method which is called from the GUI code should be public.
(*) What is Encapsulation exactly?
____________________________________________________________________
| highest precedence <---------> lowest precedence
*———————————————+———————————————+———————————+———————————————+———————
\ xCanBeSeenBy | this | any class | this subclass | any
\__________ | class | in same | in another | class
\ | nonsubbed | package | package |
Modifier of x \ | | | |
————————————————*———————————————+———————————+———————————————+———————
public | ✔ | ✔ | ✔ | ✔
————————————————+———————————————+———————————+———————————————+———————
protected | ✔ | ✔ | ✔ | ✘
————————————————+———————————————+———————————+———————————————+———————
package-private | | | |
(no modifier) | ✔ | ✔ | ✘ | ✘
————————————————+———————————————+———————————+———————————————+———————
private | ✔ | ✘ | ✘ | ✘
____________________________________________________________________
Easy rule. Start with declaring everything private. And then progress towards the public as the needs arise and design warrants it.
When exposing members ask yourself if you are exposing representation choices or abstraction choices. The first is something you want to avoid as it will introduce too many dependencies on the actual representation rather than on its observable behavior.
As a general rule I try to avoid overriding method implementations by subclassing; it's too easy to screw up the logic. Declare abstract protected methods if you intend for it to be overridden.
Also, use the #Override annotation when overriding to keep things from breaking when you refactor.
It's actually a bit more complicated than a simple grid shows. The grid tells you whether an access is allowed, but what exactly constitutes an access? Also, access levels interact with nested classes and inheritance in complex ways.
The "default" access (specified by the absence of a keyword) is also called package-private. Exception: in an interface, no modifier means public access; modifiers other than public are forbidden. Enum constants are always public.
Summary
Is an access to a member with this access specifier allowed?
Member is private: Only if member is defined within the same class as calling code.
Member is package private: Only if the calling code is within the member's immediately enclosing package.
Member is protected: Same package, or if member is defined in a superclass of the class containing the calling code.
Member is public: Yes.
What access specifiers apply to
Local variables and formal parameters cannot take access specifiers. Since they are inherently inaccessible to the outside according to scoping rules, they are effectively private.
For classes in the top scope, only public and package-private are permitted. This design choice is presumably because protected and private would be redundant at the package level (there is no inheritance of packages).
All the access specifiers are possible on class members (constructors, methods and static member functions, nested classes).
Related: Java Class Accessibility
Order
The access specifiers can be strictly ordered
public > protected > package-private > private
meaning that public provides the most access, private the least. Any reference possible on a private member is also valid for a package-private member; any reference to a package-private member is valid on a protected member, and so on. (Giving access to protected members to other classes in the same package was considered a mistake.)
Notes
A class's methods are allowed to access private members of other objects of the same class. More precisely, a method of class C can access private members of C on objects of any subclass of C. Java doesn't support restricting access by instance, only by class. (Compare with Scala, which does support it using private[this].)
You need access to a constructor to construct an object. Thus if all constructors are private, the class can only be constructed by code living within the class (typically static factory methods or static variable initializers). Similarly for package-private or protected constructors.
Only having private constructors also means that the class cannot be subclassed externally, since Java requires a subclass's constructors to implicitly or explicitly call a superclass constructor. (It can, however, contain a nested class that subclasses it.)
Inner classes
You also have to consider nested scopes, such as inner classes. An example of the complexity is that inner classes have members, which themselves can take access modifiers. So you can have a private inner class with a public member; can the member be accessed? (See below.) The general rule is to look at scope and think recursively to see whether you can access each level.
However, this is quite complicated, and for full details, consult the Java Language Specification. (Yes, there have been compiler bugs in the past.)
For a taste of how these interact, consider this example. It is possible to "leak" private inner classes; this is usually a warning:
class Test {
public static void main(final String ... args) {
System.out.println(Example.leakPrivateClass()); // OK
Example.leakPrivateClass().secretMethod(); // error
}
}
class Example {
private static class NestedClass {
public void secretMethod() {
System.out.println("Hello");
}
}
public static NestedClass leakPrivateClass() {
return new NestedClass();
}
}
Compiler output:
Test.java:4: secretMethod() in Example.NestedClass is defined in an inaccessible class or interface
Example.leakPrivateClass().secretMethod(); // error
^
1 error
Some related questions:
Java - Method accessibility inside package-private class?
As a rule of thumb:
private: class scope.
default (or package-private): package scope.
protected: package scope + child (like package, but we can subclass it from different packages). The protected modifier always keeps the "parent-child" relationship.
public: everywhere.
As a result, if we divide access right into three rights:
(D)irect (invoke from a method inside the same class, or via "this" syntax).
(R)eference (invoke a method using a reference to the class, or via "dot" syntax).
(I)nheritance (via subclassing).
then we have this simple table:
+—-———————————————+————————————+———————————+
| | Same | Different |
| | Package | Packages |
+—————————————————+————————————+———————————+
| private | D | |
+—————————————————+————————————+———————————+
| package-private | | |
| (no modifier) | D R I | |
+—————————————————+————————————+———————————+
| protected | D R I | I |
+—————————————————+————————————+———————————+
| public | D R I | R I |
+—————————————————+————————————+———————————+
In very short
public: accessible from everywhere.
protected: accessible by the classes of the same package and the subclasses residing in any package.
default (no modifier specified): accessible by the classes of the same package.
private: accessible within the same class only.
The most misunderstood access modifier in Java is protected. We know that it's similar to the default modifier with one exception in which subclasses can see it. But how? Here is an example which hopefully clarifies the confusion:
Assume that we have 2 classes; Father and Son, each in its own package:
package fatherpackage;
public class Father
{
}
-------------------------------------------
package sonpackage;
public class Son extends Father
{
}
Let's add a protected method foo() to Father.
package fatherpackage;
public class Father
{
protected void foo(){}
}
The method foo() can be called in 4 contexts:
Inside a class that is located in the same package where foo() is defined (fatherpackage):
package fatherpackage;
public class SomeClass
{
public void someMethod(Father f, Son s)
{
f.foo();
s.foo();
}
}
Inside a subclass, on the current instance via this or super:
package sonpackage;
public class Son extends Father
{
public void sonMethod()
{
this.foo();
super.foo();
}
}
On an reference whose type is the same class:
package fatherpackage;
public class Father
{
public void fatherMethod(Father f)
{
f.foo(); // valid even if foo() is private
}
}
-------------------------------------------
package sonpackage;
public class Son extends Father
{
public void sonMethod(Son s)
{
s.foo();
}
}
On an reference whose type is the parent class and it is inside the package where foo() is defined (fatherpackage) [This can be included inside context no. 1]:
package fatherpackage;
public class Son extends Father
{
public void sonMethod(Father f)
{
f.foo();
}
}
The following situations are not valid.
On an reference whose type is the parent class and it is outside the package where foo() is defined (fatherpackage):
package sonpackage;
public class Son extends Father
{
public void sonMethod(Father f)
{
f.foo(); // compilation error
}
}
A non-subclass inside a package of a subclass (A subclass inherits the protected members from its parent, and it makes them private to non-subclasses):
package sonpackage;
public class SomeClass
{
public void someMethod(Son s) throws Exception
{
s.foo(); // compilation error
}
}
Private
Methods,Variables and Constructors
Methods, Variables and Constructors that are declared private can only be accessed within the declared class itself.
Class and Interface
Private access modifier is the most restrictive access level. Class and interfaces cannot be private.
Note
Variables that are declared private can be accessed outside the class if public getter methods are present in the class.
Variables, methods and constructors which are declared protected in a superclass can be accessed only by the subclasses in other package or any class within the package of the protected members' class.
Protected
Class and Interface
The protected access modifier cannot be applied to class and interfaces.
Methods, fields can be declared protected, however methods and fields in a interface cannot be declared protected.
Note
Protected access gives the subclass a chance to use the helper method or variable, while preventing a nonrelated class from trying to use it.
Public
A class, method, constructor, interface etc declared public can be accessed from any other class.
Therefore fields, methods, blocks declared inside a public class can be accessed from any class belonging to the Java Universe.
Different Packages
However if the public class we are trying to access is in a different package, then the public class still need to be imported.
Because of class inheritance, all public methods and variables of a class are inherited by its subclasses.
Default -No keyword:
Default access modifier means we do not explicitly declare an access modifier for a class, field, method, etc.
Within the same Packages
A variable or method declared without any access control modifier is available to any other class in the same package. The fields in an interface are implicitly public static final and the methods in an interface are by default public.
Note
We cannot Override the Static fields.if you try to override it does not show any error
but it doesnot work what we except.
Related Answers
Overriding static methods in java
References links
http://docs.oracle.com/javase/tutorial/java/javaOO/accesscontrol.html
http://www.tutorialspoint.com/java/java_access_modifiers.htm
The difference can be found in the links already provided but which one to use usually comes down to the "Principle of Least Knowledge". Only allow the least visibility that is needed.
Private: Limited access to class only
Default (no modifier): Limited access to class and package
Protected: Limited access to class, package and subclasses (both inside and outside package)
Public: Accessible to class, package (all), and subclasses... In short, everywhere.
Java access modifies
Access modifier can be applicable for class, field[About], method. Try to access, subclass or override this.
Access to field or method is through a class.
Inheritance and Open Closed Principle[About]
Successor class(subclass) access modifier can be any.
Successor method(override) access modifier should be the same or expand it
Top level class(first level scope) can be public and default. Nested class[About] can have any of them
package is not applying for package hierarchy
[Swift access modifiers]
Access modifiers are there to restrict access at several levels.
Public: It is basically as simple as you can access from any class whether that is in same package or not.
To access if you are in same package you can access directly, but if you are in another package then you can create an object of the class.
Default: It is accessible in the same package from any of the class of package.
To access you can create an object of the class. But you can not access this variable outside of the package.
Protected: you can access variables in same package as well as subclass in any other package.
so basically it is default + Inherited behavior.
To access protected field defined in base class you can create object of child class.
Private: it can be access in same class.
In non-static methods you can access directly because of this reference (also in constructors)but to access in static methods you need to create object of the class.
Access modifiers in Java.
Java access modifiers are used to provide access control in Java.
1. Default:
Accessible to the classes in the same package only.
For example,
// Saved in file A.java
package pack;
class A{
void msg(){System.out.println("Hello");}
}
// Saved in file B.java
package mypack;
import pack.*;
class B{
public static void main(String args[]){
A obj = new A(); // Compile Time Error
obj.msg(); // Compile Time Error
}
}
This access is more restricted than public and protected, but less restricted than private.
2. Public
Can be accessed from anywhere. (Global Access)
For example,
// Saved in file A.java
package pack;
public class A{
public void msg(){System.out.println("Hello");}
}
// Saved in file B.java
package mypack;
import pack.*;
class B{
public static void main(String args[]){
A obj = new A();
obj.msg();
}
}
Output:Hello
3. Private
Accessible only inside the same class.
If you try to access private members on one class in another will throw compile error. For example,
class A{
private int data = 40;
private void msg(){System.out.println("Hello java");}
}
public class Simple{
public static void main(String args[]){
A obj = new A();
System.out.println(obj.data); // Compile Time Error
obj.msg(); // Compile Time Error
}
}
4. Protected
Accessible only to the classes in the same package and to the subclasses
For example,
// Saved in file A.java
package pack;
public class A{
protected void msg(){System.out.println("Hello");}
}
// Saved in file B.java
package mypack;
import pack.*;
class B extends A{
public static void main(String args[]){
B obj = new B();
obj.msg();
}
}
Output: Hello
Visible to the package. The default. No modifiers are needed.
Visible to the class only (private).
Visible to the world (public).
Visible to the package and all subclasses (protected).
Variables and methods can be declared without any modifiers that are called. Default examples:
String name = "john";
public int age(){
return age;
}
Private access modifier - private:
Methods, variables and constructors that are declared private can only be accessed within the declared class itself. The private access modifier is the most restrictive access level. Class and interfaces cannot be private.
Variables that are declared private can be accessed outside the class if public getter methods are present in the class.
Using the private modifier is the main way that an object encapsulates itself and hides data from the outside world.
Examples:
Public class Details{
private String name;
public void setName(String n){
this.name = n;
}
public String getName(){
return this.name;
}
}
Public access modifier - public:
A class, method, constructor, interface, etc. declared public can be accessed from any other class. Therefore fields, methods, blocks declared inside a public class can be accessed from any class belonging to the Java universe.
However, if the public class we are trying to access is in a different package, then the public class still need to be imported.
Because of class inheritance, all public methods and variables of a class are inherited by its subclasses.
Example:
public void cal(){
}
Protected access modifier - protected:
Variables, methods and constructors which are declared protected in a superclass can be accessed only by the subclasses in another package or any class within the package of the protected members' class.
The protected access modifier cannot be applied to class and interfaces. Methods, fields can be declared protected, however methods and fields in a interface cannot be declared protected.
Protected access gives the subclass a chance to use the helper method or variable, while preventing a nonrelated class from trying to use it.
class Van{
protected boolean speed(){
}
}
class Car{
boolean speed(){
}
}
public - accessible from anywhere in the application.
default - accessible from package.
protected - accessible from package and sub-classes in other package.
as well
private - accessible from its class only.
This page writes well about the protected & default access modifier
....
Protected: Protected access modifier is the a little tricky and you can say is a superset of the default access modifier. Protected members are same as the default members as far as the access in the same package is concerned. The difference is that, the protected members are also accessible to the subclasses of the class in which the member is declared which are outside the package in which the parent class is present.
But these protected members are “accessible outside the package only through inheritance“. i.e you can access a protected member of a class in its subclass present in some other package directly as if the member is present in the subclass itself. But that protected member will not be accessible in the subclass outside the package by using parent class’s reference.
....
David's answer provides the meaning of each access modifier. As for when to use each, I'd suggest making public all classes and the methods of each class that are meant for external use (its API), and everything else private.
Over time you'll develop a sense for when to make some classes package-private and when to declare certain methods protected for use in subclasses.
This image will make you understand easily about the basic differences between public, private, protected and default access modifiers. The default modifier takes place automatically when you don't declare ant access modifiers in your code.
Public Protected Default and private are access modifiers.
They are meant for encapsulation, or hiding and showing contents of the class.
Class can be public or default
Class members can be public, protected, default or private.
Private is not accessible outside the class
Default is accessible only in the package.
Protected in package as well as any class which extends it.
Public is open for all.
Normally, member variables are defined private, but member methods are public.
Note: This is just a supplement for the accepted answer.
This is related to Java Access Modifiers.
From Java Access Modifiers:
A Java access modifier specifies which classes can access a given
class and its fields, constructors and methods. Access modifiers can
be specified separately for a class, its constructors, fields and
methods. Java access modifiers are also sometimes referred to in daily
speech as Java access specifiers, but the correct name is Java access
modifiers. Classes, fields, constructors and methods can have one of
four different Java access modifiers:
List item
private
default (package)
protected
public
From Controlling Access to Members of a Class tutorials:
Access level modifiers determine whether other classes can use a
particular field or invoke a particular method. There are two levels
of access control:
At the top level—public, or package-private (no explicit modifier).
At the member level—public, private, protected, or package-private (no explicit modifier).
A class may be declared with the modifier public, in which case that
class is visible to all classes everywhere. If a class has no modifier
(the default, also known as package-private), it is visible only
within its own package
The following table shows the access to members permitted by each
modifier.
╔═════════════╦═══════╦═════════╦══════════╦═══════╗
║ Modifier ║ Class ║ Package ║ Subclass ║ World ║
╠═════════════╬═══════╬═════════╬══════════╬═══════╣
║ public ║ Y ║ Y ║ Y ║ Y ║
║ protected ║ Y ║ Y ║ Y ║ N ║
║ no modifier ║ Y ║ Y ║ N ║ N ║
║ private ║ Y ║ N ║ N ║ N ║
╚═════════════╩═══════╩═════════╩══════════╩═══════╝
The first data column indicates whether the class itself has access to
the member defined by the access level. As you can see, a class always
has access to its own members. The second column indicates whether
classes in the same package as the class (regardless of their
parentage) have access to the member. The third column indicates
whether subclasses of the class declared outside this package have
access to the member. The fourth column indicates whether all classes
have access to the member.
Access levels affect you in two ways. First, when you use classes that
come from another source, such as the classes in the Java platform,
access levels determine which members of those classes your own
classes can use. Second, when you write a class, you need to decide
what access level every member variable and every method in your class
should have.
Often times I've realized that remembering the basic concepts of any language can made possible by creating real-world analogies. Here is my analogy for understanding access modifiers in Java:
Let's assume that you're a student at a university and you have a friend who's coming to visit you over the weekend. Suppose there exists a big statue of the university's founder in the middle of the campus.
When you bring him to the campus, the first thing that you and your friend sees is this statue. This means that anyone who walks in the campus can look at the statue without the university's permission. This makes the statue as PUBLIC.
Next, you want to take your friend to your dorm, but for that you need to register him as a visitor. This means that he gets an access pass (which is the same as yours) to get into various buildings on campus. This would make his access card as PROTECTED.
Your friend wants to login to the campus WiFi but doesn't have the any credentials to do so. The only way he can get online is if you share your login with him. (Remember, every student who goes to the university also possesses these login credentials). This would make your login credentials as NO MODIFIER.
Finally, your friend wants to read your progress report for the semester which is posted on the website. However, every student has their own personal login to access this section of the campus website. This would make these credentials as PRIVATE.
Hope this helps!
When you are thinking of access modifiers just think of it in this way (applies to both variables and methods):
public --> accessible from every where
private --> accessible only within the same class where it is declared
Now the confusion arises when it comes to default and protected
default --> No access modifier keyword is present. This means it is available strictly within the package of the class. Nowhere outside that package it can be accessed.
protected --> Slightly less stricter than default and apart from the same package classes it can be accessed by sub classes outside the package it is declared.
It is all about encapsulation (or as Joe Phillips stated, least knowledge).
Start with the most restrictive (private) and see if you need less restrictive modifiers later on.
We all use method and member modifiers like private, public, ... but one thing too few developers do is use packages to organize code logically.
For example:
You may put sensitive security methods in a 'security' package.
Then put a public class which accesses some of the security related code in this package but keep other security classes package private.
Thus other developers will only be able to use the publicly available class from outside of this package (unless they change the modifier).
This is not a security feature, but will guide usage.
Outside world -> Package (SecurityEntryClass ---> Package private classes)
Another thing is that classes which depend a lot on each other may end up in the same package and could eventually be refactored or merged if the dependency is too strong.
If on the contrary you set everything as public it will not be clear what should or should not be accessed, which may lead to writing a lot of javadoc (which does not enforce anything via the compiler...).
My two cents :)
private:
class -> a top level class cannot be private. inner classes can be private which are accessible from same class.
instance variable -> accessible only in the class. Cannot access outside the class.
package-private:
class -> a top level class can be package-private. It can only be accessible from same package. Not from sub package, not from outside package.
instance variable -> accessible from same package. Not from sub package, not from outside package.
protected:
class -> a top level class cannot be protected.
instance variable -> Only accessible in same package or subpackage. Can only be access outside the package while extending class.
public:
class -> accessible from package/subpackage/another package
instance variable -> accessible from package/subpackage/another package
Here is detailed answer
https://github.com/junto06/java-4-beginners/blob/master/basics/access-modifier.md
For beginners considering this example can be helpful;
Consider I have developed MyClass in foo package and it has a fantastic method named print which you are interested in calling it ( it could be a method or property )
package foo; // I am in foo
public class MyClass {
private void print() { //This is private
System.out.println("I can print!");
}
}
You have developed YourClass in bar package, and you are interested to use MyClass#print
package bar; \\You are not in same package as me
import foo.MyClass;
public class YourClass {
void test() {
MyClass myClass = new MyClass();
myClass.print();
}
}
Your code is not compile and you get error The method print() is undefined for the type MyClass
You come to me:
You: I want to use your method but it is private. Can you make it public?
Me : No I don't want others use it
You: I am your friend at least let me not others use it.
Me : Ok I will remove the private keyword. My Access modifier will be default or private package. As you are my friend you must be in same package as me. So you must come to my package foo. I mean exact package not even a sub package.
Then MyClass will be
package foo;
public class MyClass {
void print() { //No access modifier means default or package-private
System.out.println("I can print!");
}
}
YourClass will be :
package foo;//You come to my package
public class YourClass {
void test() {
MyClass myClass = new MyClass();
myClass.print();
}
}
No consider this: Again you come to me
You: My boss told me I can not change my package ( In actual world you can not change you package to use other classes methods)
Me : There is another way, if you extend me and I make print() protected, then you can use it whether you change you package or not. ( So sub classing will always give you access to my method).
Here is MyClass
package foo;
protected class MyClass { // it is now protected
protected void print() {
System.out.println("I can print!");
}
}
Here is YourClass
package bar; // You are on your own package
import foo.MyClass;
public class YourClass extends MyClass {
void test() {
//You initiate yourself! But as you extend me you can call my print()
YourClass yourClass = new YourClass();
yourClass.print();
}
}
You may have noticed that by making a method protected all other classes can use it by extending it, you can not easily control how can use it. This was solved in java 17 by introducing sealed and permits words. So you can define which classes can extend you. By something like public sealed class MyClass permits YourClass
See What are sealed classes in Java 17? for more info
public
If a class member is declared with public then it can be accessed from anywhere
protected
If a class member is declared with keyword protected then it can be accessed from same class members, outside class members within the same package and inherited class members. If a class member is protected then it can NOT be accessed from outside package class unless the outside packaged class is inherited i.e. extends the other package superclass. But a protected class member is always available to same package classes it does NOT matter weather the same package class is inherited or NOT
default
In Java default is NOT an access modifier keyword. If a class member is declared without any access modifier keyword then in this case it is considered as default member. The default class member is always available to same package class members. But outside package class member can NOT access default class members even if outside classes are subclasses unlike protected members
private
If a class member is declared with keyword protected then in this case it is available ONLY to same class members
when talking about access modifiers we can easy to understand, very simple rules include them.
Private Access modifier use in: - Only same class
Default Access modifier use in: - Only same class / Same package subclasses
Protected Access modifier use in: - same class / Same package subclasses / Same package non - subclasses / Different package subclasses
Public Access modifier use in:- we can use anywhere (same class / Same package subclasses / Same package non - subclasses / Different package subclasses/ Different package non - subclasses)
Access Specifiers in Java:
There are 4 access specifiers in java, namely private, package-private (default), protected and public in increasing access order.
Private:
When you are developing some class and you want member of this class not to be exposed outside this class then you should declare it as private. private members can be accessed only in class where they are defined i.e. enclosing class. private members can be accessed on 'this' reference and also on other instances of class enclosing these members, but only within the definition of this class.
Package-private (default):
This access specifier will provide access specified by private access specifier in addition to access described below.
When you are developing some package and hence some class (say Class1) within it, you may use default (need not be mentioned explicitly) access specifier, to expose member within class, to other classes within your (same) package. In these other classes (within same package), you can access these default members on instance of Class1. Also you can access these default members within subclasses of Class1, say Class2 (on this reference or on instance of Class1 or on instance of Class2).
Basically, within same package you can access default members on instance of class directly or on 'this' reference in subclasses.
protected:
This access specifier will provide access specified by package-private access specifier in addition to access described below.
When you are developing some package and hence some class (say Class1) within it, then you should use protected access specifier for data member within Class1 if you don't want this member to be accessed outside your package (say in package of consumer of your package i.e. client who is using your APIs) in general, but you want to make an exception and allow access to this member only if client writes class say Class2 that extends Class1. So, in general, protected members will be accessible on 'this' reference in derived classes i.e. Class2 and also on explicit instances of Class2.
Please note:
You won't be able to access inherited protected member of Class1 in
Class2, if you attempt to access it on explicit instance of Class1,
although it is inherited in it.
When you write another class Class3 within same/different package
that extends Class2, protected member from Class1 will be accessible
on this reference and also on explicit instance of Class3. This will
be true for any hierarchy that is extended i.e. protected member
will still be accessible on this reference or instance of extended
class. Note that in Class3, if you create instance of Class2 then
you will not be able to access protected member from Class1 though
it is inherited.
So bottom line is, protected members can be accessed in other packages, only if some class from this other package, extends class enclosing this protected member and protected member is accessed on 'this' reference or explicit instances of extended class, within definition of extended class.
public: This access specifier will provide access specified by protected access specifier in addition to access described below.
When you are developing some package and hence some class (say Class1) within it, then you should use public access specifier for data member within Class1 if you want this member to be accessible in other packages on instance of Class1 created in some class of other package. Basically this access specifier should be used when you intent to expose your data member to world without any condition.
In Java, are there clear rules on when to use each of access modifiers, namely the default (package private), public, protected and private, while making class and interface and dealing with inheritance?
The official tutorial may be of some use to you.
Class
Package
Subclass(same pkg)
Subclass(diff pkg)
World
public
+
+
+
+
+
protected
+
+
+
+
no modifier
+
+
+
private
+
+ : accessible
blank : not accessible
(Caveat: I am not a Java programmer, I am a Perl programmer. Perl has no formal protections which is perhaps why I understand the problem so well :) )
Private
Like you'd think, only the class in which it is declared can see it.
Package Private
It can only be seen and used by the package in which it was declared. This is the default in Java (which some see as a mistake).
Protected
Package Private + can be seen by subclasses or package members.
Public
Everyone can see it.
Published
Visible outside the code I control. (While not Java syntax, it is important for this discussion).
C++ defines an additional level called "friend" and the less you know about that the better.
When should you use what? The whole idea is encapsulation to hide information. As much as possible you want to hide the detail of how something is done from your users. Why? Because then you can change them later and not break anybody's code. This lets you optimize, refactor, redesign, and fix bugs without worrying that someone was using that code you just overhauled.
So, the rule of thumb is to make things only as visible as they have to be. Start with private and only add more visibility as needed. Only make public that which is necessary for the user to know, every detail you make public cramps your ability to redesign the system.
If you want users to be able to customize behaviors, rather than making internals public so they can override them, it's often a better idea to shove those guts into an object and make that interface public. That way they can simply plug in a new object. For example, if you were writing a CD player and wanted the "go find info about this CD" bit customizable, rather than make those methods public you'd put all that functionality into its object and make just your object getter/setter public. In this way being stingy about exposing your guts encourages good composition and separation of concerns
I stick with just "private" and "public". Many OO languages just have that. "Protected" can be handy, but it's a cheat. Once an interface is more than private it's outside of your control and you have to go looking in other people's code to find uses.
This is where the idea of "published" comes in. Changing an interface (refactoring it) requires that you find all the code which is using it and change that, too. If the interface is private, well no problem. If it's protected you have to go find all your subclasses. If it's public you have to go find all the code which uses your code. Sometimes this is possible, for example, if you're working on corporate code that's for internal use only it doesn't matter if an interface is public. You can grab all the code out of the corporate repository. But if an interface is "published", if there is code using it outside your control, then you're hosed. You must support that interface or risk breaking code. Even protected interfaces can be considered published (which is why I don't bother with protected).
Many languages find the hierarchical nature of public/protected/private to be too limiting and not in line with reality. To that end, there is the concept of a trait class, but that's another show.
Here's a better version of the table, that also includes a column for modules.
Explanations
A private member (i) is only accessible within the same class as it is declared.
A member with no access modifier (j) is only accessible within classes in the same package.
A protected member (k) is accessible within all classes in the same package and within subclasses in other packages.
A public member (l) is accessible to all classes (unless it resides in a module that does not export the package it is declared in).
Which modifier to choose?
Access modifiers is a tool to help you to prevent accidentally breaking encapsulation(*). Ask yourself if you intend the member to be something that's internal to the class, package, class hierarchy or not internal at all, and choose access level accordingly.
Examples:
A field long internalCounter should probably be private since it's mutable and an implementation detail.
A class that should only be instantiated in a factory class (in the same package) should have a package restricted constructor, since it shouldn't be possible to call it directly from outside the package.
An internal void beforeRender() method called right before rendering and used as a hook in subclasses should be protected.
A void saveGame(File dst) method which is called from the GUI code should be public.
(*) What is Encapsulation exactly?
____________________________________________________________________
| highest precedence <---------> lowest precedence
*———————————————+———————————————+———————————+———————————————+———————
\ xCanBeSeenBy | this | any class | this subclass | any
\__________ | class | in same | in another | class
\ | nonsubbed | package | package |
Modifier of x \ | | | |
————————————————*———————————————+———————————+———————————————+———————
public | ✔ | ✔ | ✔ | ✔
————————————————+———————————————+———————————+———————————————+———————
protected | ✔ | ✔ | ✔ | ✘
————————————————+———————————————+———————————+———————————————+———————
package-private | | | |
(no modifier) | ✔ | ✔ | ✘ | ✘
————————————————+———————————————+———————————+———————————————+———————
private | ✔ | ✘ | ✘ | ✘
____________________________________________________________________
Easy rule. Start with declaring everything private. And then progress towards the public as the needs arise and design warrants it.
When exposing members ask yourself if you are exposing representation choices or abstraction choices. The first is something you want to avoid as it will introduce too many dependencies on the actual representation rather than on its observable behavior.
As a general rule I try to avoid overriding method implementations by subclassing; it's too easy to screw up the logic. Declare abstract protected methods if you intend for it to be overridden.
Also, use the #Override annotation when overriding to keep things from breaking when you refactor.
It's actually a bit more complicated than a simple grid shows. The grid tells you whether an access is allowed, but what exactly constitutes an access? Also, access levels interact with nested classes and inheritance in complex ways.
The "default" access (specified by the absence of a keyword) is also called package-private. Exception: in an interface, no modifier means public access; modifiers other than public are forbidden. Enum constants are always public.
Summary
Is an access to a member with this access specifier allowed?
Member is private: Only if member is defined within the same class as calling code.
Member is package private: Only if the calling code is within the member's immediately enclosing package.
Member is protected: Same package, or if member is defined in a superclass of the class containing the calling code.
Member is public: Yes.
What access specifiers apply to
Local variables and formal parameters cannot take access specifiers. Since they are inherently inaccessible to the outside according to scoping rules, they are effectively private.
For classes in the top scope, only public and package-private are permitted. This design choice is presumably because protected and private would be redundant at the package level (there is no inheritance of packages).
All the access specifiers are possible on class members (constructors, methods and static member functions, nested classes).
Related: Java Class Accessibility
Order
The access specifiers can be strictly ordered
public > protected > package-private > private
meaning that public provides the most access, private the least. Any reference possible on a private member is also valid for a package-private member; any reference to a package-private member is valid on a protected member, and so on. (Giving access to protected members to other classes in the same package was considered a mistake.)
Notes
A class's methods are allowed to access private members of other objects of the same class. More precisely, a method of class C can access private members of C on objects of any subclass of C. Java doesn't support restricting access by instance, only by class. (Compare with Scala, which does support it using private[this].)
You need access to a constructor to construct an object. Thus if all constructors are private, the class can only be constructed by code living within the class (typically static factory methods or static variable initializers). Similarly for package-private or protected constructors.
Only having private constructors also means that the class cannot be subclassed externally, since Java requires a subclass's constructors to implicitly or explicitly call a superclass constructor. (It can, however, contain a nested class that subclasses it.)
Inner classes
You also have to consider nested scopes, such as inner classes. An example of the complexity is that inner classes have members, which themselves can take access modifiers. So you can have a private inner class with a public member; can the member be accessed? (See below.) The general rule is to look at scope and think recursively to see whether you can access each level.
However, this is quite complicated, and for full details, consult the Java Language Specification. (Yes, there have been compiler bugs in the past.)
For a taste of how these interact, consider this example. It is possible to "leak" private inner classes; this is usually a warning:
class Test {
public static void main(final String ... args) {
System.out.println(Example.leakPrivateClass()); // OK
Example.leakPrivateClass().secretMethod(); // error
}
}
class Example {
private static class NestedClass {
public void secretMethod() {
System.out.println("Hello");
}
}
public static NestedClass leakPrivateClass() {
return new NestedClass();
}
}
Compiler output:
Test.java:4: secretMethod() in Example.NestedClass is defined in an inaccessible class or interface
Example.leakPrivateClass().secretMethod(); // error
^
1 error
Some related questions:
Java - Method accessibility inside package-private class?
As a rule of thumb:
private: class scope.
default (or package-private): package scope.
protected: package scope + child (like package, but we can subclass it from different packages). The protected modifier always keeps the "parent-child" relationship.
public: everywhere.
As a result, if we divide access right into three rights:
(D)irect (invoke from a method inside the same class, or via "this" syntax).
(R)eference (invoke a method using a reference to the class, or via "dot" syntax).
(I)nheritance (via subclassing).
then we have this simple table:
+—-———————————————+————————————+———————————+
| | Same | Different |
| | Package | Packages |
+—————————————————+————————————+———————————+
| private | D | |
+—————————————————+————————————+———————————+
| package-private | | |
| (no modifier) | D R I | |
+—————————————————+————————————+———————————+
| protected | D R I | I |
+—————————————————+————————————+———————————+
| public | D R I | R I |
+—————————————————+————————————+———————————+
In very short
public: accessible from everywhere.
protected: accessible by the classes of the same package and the subclasses residing in any package.
default (no modifier specified): accessible by the classes of the same package.
private: accessible within the same class only.
The most misunderstood access modifier in Java is protected. We know that it's similar to the default modifier with one exception in which subclasses can see it. But how? Here is an example which hopefully clarifies the confusion:
Assume that we have 2 classes; Father and Son, each in its own package:
package fatherpackage;
public class Father
{
}
-------------------------------------------
package sonpackage;
public class Son extends Father
{
}
Let's add a protected method foo() to Father.
package fatherpackage;
public class Father
{
protected void foo(){}
}
The method foo() can be called in 4 contexts:
Inside a class that is located in the same package where foo() is defined (fatherpackage):
package fatherpackage;
public class SomeClass
{
public void someMethod(Father f, Son s)
{
f.foo();
s.foo();
}
}
Inside a subclass, on the current instance via this or super:
package sonpackage;
public class Son extends Father
{
public void sonMethod()
{
this.foo();
super.foo();
}
}
On an reference whose type is the same class:
package fatherpackage;
public class Father
{
public void fatherMethod(Father f)
{
f.foo(); // valid even if foo() is private
}
}
-------------------------------------------
package sonpackage;
public class Son extends Father
{
public void sonMethod(Son s)
{
s.foo();
}
}
On an reference whose type is the parent class and it is inside the package where foo() is defined (fatherpackage) [This can be included inside context no. 1]:
package fatherpackage;
public class Son extends Father
{
public void sonMethod(Father f)
{
f.foo();
}
}
The following situations are not valid.
On an reference whose type is the parent class and it is outside the package where foo() is defined (fatherpackage):
package sonpackage;
public class Son extends Father
{
public void sonMethod(Father f)
{
f.foo(); // compilation error
}
}
A non-subclass inside a package of a subclass (A subclass inherits the protected members from its parent, and it makes them private to non-subclasses):
package sonpackage;
public class SomeClass
{
public void someMethod(Son s) throws Exception
{
s.foo(); // compilation error
}
}
Private
Methods,Variables and Constructors
Methods, Variables and Constructors that are declared private can only be accessed within the declared class itself.
Class and Interface
Private access modifier is the most restrictive access level. Class and interfaces cannot be private.
Note
Variables that are declared private can be accessed outside the class if public getter methods are present in the class.
Variables, methods and constructors which are declared protected in a superclass can be accessed only by the subclasses in other package or any class within the package of the protected members' class.
Protected
Class and Interface
The protected access modifier cannot be applied to class and interfaces.
Methods, fields can be declared protected, however methods and fields in a interface cannot be declared protected.
Note
Protected access gives the subclass a chance to use the helper method or variable, while preventing a nonrelated class from trying to use it.
Public
A class, method, constructor, interface etc declared public can be accessed from any other class.
Therefore fields, methods, blocks declared inside a public class can be accessed from any class belonging to the Java Universe.
Different Packages
However if the public class we are trying to access is in a different package, then the public class still need to be imported.
Because of class inheritance, all public methods and variables of a class are inherited by its subclasses.
Default -No keyword:
Default access modifier means we do not explicitly declare an access modifier for a class, field, method, etc.
Within the same Packages
A variable or method declared without any access control modifier is available to any other class in the same package. The fields in an interface are implicitly public static final and the methods in an interface are by default public.
Note
We cannot Override the Static fields.if you try to override it does not show any error
but it doesnot work what we except.
Related Answers
Overriding static methods in java
References links
http://docs.oracle.com/javase/tutorial/java/javaOO/accesscontrol.html
http://www.tutorialspoint.com/java/java_access_modifiers.htm
The difference can be found in the links already provided but which one to use usually comes down to the "Principle of Least Knowledge". Only allow the least visibility that is needed.
Private: Limited access to class only
Default (no modifier): Limited access to class and package
Protected: Limited access to class, package and subclasses (both inside and outside package)
Public: Accessible to class, package (all), and subclasses... In short, everywhere.
Java access modifies
Access modifier can be applicable for class, field[About], method. Try to access, subclass or override this.
Access to field or method is through a class.
Inheritance and Open Closed Principle[About]
Successor class(subclass) access modifier can be any.
Successor method(override) access modifier should be the same or expand it
Top level class(first level scope) can be public and default. Nested class[About] can have any of them
package is not applying for package hierarchy
[Swift access modifiers]
Access modifiers are there to restrict access at several levels.
Public: It is basically as simple as you can access from any class whether that is in same package or not.
To access if you are in same package you can access directly, but if you are in another package then you can create an object of the class.
Default: It is accessible in the same package from any of the class of package.
To access you can create an object of the class. But you can not access this variable outside of the package.
Protected: you can access variables in same package as well as subclass in any other package.
so basically it is default + Inherited behavior.
To access protected field defined in base class you can create object of child class.
Private: it can be access in same class.
In non-static methods you can access directly because of this reference (also in constructors)but to access in static methods you need to create object of the class.
Access modifiers in Java.
Java access modifiers are used to provide access control in Java.
1. Default:
Accessible to the classes in the same package only.
For example,
// Saved in file A.java
package pack;
class A{
void msg(){System.out.println("Hello");}
}
// Saved in file B.java
package mypack;
import pack.*;
class B{
public static void main(String args[]){
A obj = new A(); // Compile Time Error
obj.msg(); // Compile Time Error
}
}
This access is more restricted than public and protected, but less restricted than private.
2. Public
Can be accessed from anywhere. (Global Access)
For example,
// Saved in file A.java
package pack;
public class A{
public void msg(){System.out.println("Hello");}
}
// Saved in file B.java
package mypack;
import pack.*;
class B{
public static void main(String args[]){
A obj = new A();
obj.msg();
}
}
Output:Hello
3. Private
Accessible only inside the same class.
If you try to access private members on one class in another will throw compile error. For example,
class A{
private int data = 40;
private void msg(){System.out.println("Hello java");}
}
public class Simple{
public static void main(String args[]){
A obj = new A();
System.out.println(obj.data); // Compile Time Error
obj.msg(); // Compile Time Error
}
}
4. Protected
Accessible only to the classes in the same package and to the subclasses
For example,
// Saved in file A.java
package pack;
public class A{
protected void msg(){System.out.println("Hello");}
}
// Saved in file B.java
package mypack;
import pack.*;
class B extends A{
public static void main(String args[]){
B obj = new B();
obj.msg();
}
}
Output: Hello
Visible to the package. The default. No modifiers are needed.
Visible to the class only (private).
Visible to the world (public).
Visible to the package and all subclasses (protected).
Variables and methods can be declared without any modifiers that are called. Default examples:
String name = "john";
public int age(){
return age;
}
Private access modifier - private:
Methods, variables and constructors that are declared private can only be accessed within the declared class itself. The private access modifier is the most restrictive access level. Class and interfaces cannot be private.
Variables that are declared private can be accessed outside the class if public getter methods are present in the class.
Using the private modifier is the main way that an object encapsulates itself and hides data from the outside world.
Examples:
Public class Details{
private String name;
public void setName(String n){
this.name = n;
}
public String getName(){
return this.name;
}
}
Public access modifier - public:
A class, method, constructor, interface, etc. declared public can be accessed from any other class. Therefore fields, methods, blocks declared inside a public class can be accessed from any class belonging to the Java universe.
However, if the public class we are trying to access is in a different package, then the public class still need to be imported.
Because of class inheritance, all public methods and variables of a class are inherited by its subclasses.
Example:
public void cal(){
}
Protected access modifier - protected:
Variables, methods and constructors which are declared protected in a superclass can be accessed only by the subclasses in another package or any class within the package of the protected members' class.
The protected access modifier cannot be applied to class and interfaces. Methods, fields can be declared protected, however methods and fields in a interface cannot be declared protected.
Protected access gives the subclass a chance to use the helper method or variable, while preventing a nonrelated class from trying to use it.
class Van{
protected boolean speed(){
}
}
class Car{
boolean speed(){
}
}
public - accessible from anywhere in the application.
default - accessible from package.
protected - accessible from package and sub-classes in other package.
as well
private - accessible from its class only.
This page writes well about the protected & default access modifier
....
Protected: Protected access modifier is the a little tricky and you can say is a superset of the default access modifier. Protected members are same as the default members as far as the access in the same package is concerned. The difference is that, the protected members are also accessible to the subclasses of the class in which the member is declared which are outside the package in which the parent class is present.
But these protected members are “accessible outside the package only through inheritance“. i.e you can access a protected member of a class in its subclass present in some other package directly as if the member is present in the subclass itself. But that protected member will not be accessible in the subclass outside the package by using parent class’s reference.
....
David's answer provides the meaning of each access modifier. As for when to use each, I'd suggest making public all classes and the methods of each class that are meant for external use (its API), and everything else private.
Over time you'll develop a sense for when to make some classes package-private and when to declare certain methods protected for use in subclasses.
This image will make you understand easily about the basic differences between public, private, protected and default access modifiers. The default modifier takes place automatically when you don't declare ant access modifiers in your code.
Public Protected Default and private are access modifiers.
They are meant for encapsulation, or hiding and showing contents of the class.
Class can be public or default
Class members can be public, protected, default or private.
Private is not accessible outside the class
Default is accessible only in the package.
Protected in package as well as any class which extends it.
Public is open for all.
Normally, member variables are defined private, but member methods are public.
Note: This is just a supplement for the accepted answer.
This is related to Java Access Modifiers.
From Java Access Modifiers:
A Java access modifier specifies which classes can access a given
class and its fields, constructors and methods. Access modifiers can
be specified separately for a class, its constructors, fields and
methods. Java access modifiers are also sometimes referred to in daily
speech as Java access specifiers, but the correct name is Java access
modifiers. Classes, fields, constructors and methods can have one of
four different Java access modifiers:
List item
private
default (package)
protected
public
From Controlling Access to Members of a Class tutorials:
Access level modifiers determine whether other classes can use a
particular field or invoke a particular method. There are two levels
of access control:
At the top level—public, or package-private (no explicit modifier).
At the member level—public, private, protected, or package-private (no explicit modifier).
A class may be declared with the modifier public, in which case that
class is visible to all classes everywhere. If a class has no modifier
(the default, also known as package-private), it is visible only
within its own package
The following table shows the access to members permitted by each
modifier.
╔═════════════╦═══════╦═════════╦══════════╦═══════╗
║ Modifier ║ Class ║ Package ║ Subclass ║ World ║
╠═════════════╬═══════╬═════════╬══════════╬═══════╣
║ public ║ Y ║ Y ║ Y ║ Y ║
║ protected ║ Y ║ Y ║ Y ║ N ║
║ no modifier ║ Y ║ Y ║ N ║ N ║
║ private ║ Y ║ N ║ N ║ N ║
╚═════════════╩═══════╩═════════╩══════════╩═══════╝
The first data column indicates whether the class itself has access to
the member defined by the access level. As you can see, a class always
has access to its own members. The second column indicates whether
classes in the same package as the class (regardless of their
parentage) have access to the member. The third column indicates
whether subclasses of the class declared outside this package have
access to the member. The fourth column indicates whether all classes
have access to the member.
Access levels affect you in two ways. First, when you use classes that
come from another source, such as the classes in the Java platform,
access levels determine which members of those classes your own
classes can use. Second, when you write a class, you need to decide
what access level every member variable and every method in your class
should have.
Often times I've realized that remembering the basic concepts of any language can made possible by creating real-world analogies. Here is my analogy for understanding access modifiers in Java:
Let's assume that you're a student at a university and you have a friend who's coming to visit you over the weekend. Suppose there exists a big statue of the university's founder in the middle of the campus.
When you bring him to the campus, the first thing that you and your friend sees is this statue. This means that anyone who walks in the campus can look at the statue without the university's permission. This makes the statue as PUBLIC.
Next, you want to take your friend to your dorm, but for that you need to register him as a visitor. This means that he gets an access pass (which is the same as yours) to get into various buildings on campus. This would make his access card as PROTECTED.
Your friend wants to login to the campus WiFi but doesn't have the any credentials to do so. The only way he can get online is if you share your login with him. (Remember, every student who goes to the university also possesses these login credentials). This would make your login credentials as NO MODIFIER.
Finally, your friend wants to read your progress report for the semester which is posted on the website. However, every student has their own personal login to access this section of the campus website. This would make these credentials as PRIVATE.
Hope this helps!
When you are thinking of access modifiers just think of it in this way (applies to both variables and methods):
public --> accessible from every where
private --> accessible only within the same class where it is declared
Now the confusion arises when it comes to default and protected
default --> No access modifier keyword is present. This means it is available strictly within the package of the class. Nowhere outside that package it can be accessed.
protected --> Slightly less stricter than default and apart from the same package classes it can be accessed by sub classes outside the package it is declared.
It is all about encapsulation (or as Joe Phillips stated, least knowledge).
Start with the most restrictive (private) and see if you need less restrictive modifiers later on.
We all use method and member modifiers like private, public, ... but one thing too few developers do is use packages to organize code logically.
For example:
You may put sensitive security methods in a 'security' package.
Then put a public class which accesses some of the security related code in this package but keep other security classes package private.
Thus other developers will only be able to use the publicly available class from outside of this package (unless they change the modifier).
This is not a security feature, but will guide usage.
Outside world -> Package (SecurityEntryClass ---> Package private classes)
Another thing is that classes which depend a lot on each other may end up in the same package and could eventually be refactored or merged if the dependency is too strong.
If on the contrary you set everything as public it will not be clear what should or should not be accessed, which may lead to writing a lot of javadoc (which does not enforce anything via the compiler...).
My two cents :)
private:
class -> a top level class cannot be private. inner classes can be private which are accessible from same class.
instance variable -> accessible only in the class. Cannot access outside the class.
package-private:
class -> a top level class can be package-private. It can only be accessible from same package. Not from sub package, not from outside package.
instance variable -> accessible from same package. Not from sub package, not from outside package.
protected:
class -> a top level class cannot be protected.
instance variable -> Only accessible in same package or subpackage. Can only be access outside the package while extending class.
public:
class -> accessible from package/subpackage/another package
instance variable -> accessible from package/subpackage/another package
Here is detailed answer
https://github.com/junto06/java-4-beginners/blob/master/basics/access-modifier.md
For beginners considering this example can be helpful;
Consider I have developed MyClass in foo package and it has a fantastic method named print which you are interested in calling it ( it could be a method or property )
package foo; // I am in foo
public class MyClass {
private void print() { //This is private
System.out.println("I can print!");
}
}
You have developed YourClass in bar package, and you are interested to use MyClass#print
package bar; \\You are not in same package as me
import foo.MyClass;
public class YourClass {
void test() {
MyClass myClass = new MyClass();
myClass.print();
}
}
Your code is not compile and you get error The method print() is undefined for the type MyClass
You come to me:
You: I want to use your method but it is private. Can you make it public?
Me : No I don't want others use it
You: I am your friend at least let me not others use it.
Me : Ok I will remove the private keyword. My Access modifier will be default or private package. As you are my friend you must be in same package as me. So you must come to my package foo. I mean exact package not even a sub package.
Then MyClass will be
package foo;
public class MyClass {
void print() { //No access modifier means default or package-private
System.out.println("I can print!");
}
}
YourClass will be :
package foo;//You come to my package
public class YourClass {
void test() {
MyClass myClass = new MyClass();
myClass.print();
}
}
No consider this: Again you come to me
You: My boss told me I can not change my package ( In actual world you can not change you package to use other classes methods)
Me : There is another way, if you extend me and I make print() protected, then you can use it whether you change you package or not. ( So sub classing will always give you access to my method).
Here is MyClass
package foo;
protected class MyClass { // it is now protected
protected void print() {
System.out.println("I can print!");
}
}
Here is YourClass
package bar; // You are on your own package
import foo.MyClass;
public class YourClass extends MyClass {
void test() {
//You initiate yourself! But as you extend me you can call my print()
YourClass yourClass = new YourClass();
yourClass.print();
}
}
You may have noticed that by making a method protected all other classes can use it by extending it, you can not easily control how can use it. This was solved in java 17 by introducing sealed and permits words. So you can define which classes can extend you. By something like public sealed class MyClass permits YourClass
See What are sealed classes in Java 17? for more info
public
If a class member is declared with public then it can be accessed from anywhere
protected
If a class member is declared with keyword protected then it can be accessed from same class members, outside class members within the same package and inherited class members. If a class member is protected then it can NOT be accessed from outside package class unless the outside packaged class is inherited i.e. extends the other package superclass. But a protected class member is always available to same package classes it does NOT matter weather the same package class is inherited or NOT
default
In Java default is NOT an access modifier keyword. If a class member is declared without any access modifier keyword then in this case it is considered as default member. The default class member is always available to same package class members. But outside package class member can NOT access default class members even if outside classes are subclasses unlike protected members
private
If a class member is declared with keyword protected then in this case it is available ONLY to same class members
when talking about access modifiers we can easy to understand, very simple rules include them.
Private Access modifier use in: - Only same class
Default Access modifier use in: - Only same class / Same package subclasses
Protected Access modifier use in: - same class / Same package subclasses / Same package non - subclasses / Different package subclasses
Public Access modifier use in:- we can use anywhere (same class / Same package subclasses / Same package non - subclasses / Different package subclasses/ Different package non - subclasses)
Access Specifiers in Java:
There are 4 access specifiers in java, namely private, package-private (default), protected and public in increasing access order.
Private:
When you are developing some class and you want member of this class not to be exposed outside this class then you should declare it as private. private members can be accessed only in class where they are defined i.e. enclosing class. private members can be accessed on 'this' reference and also on other instances of class enclosing these members, but only within the definition of this class.
Package-private (default):
This access specifier will provide access specified by private access specifier in addition to access described below.
When you are developing some package and hence some class (say Class1) within it, you may use default (need not be mentioned explicitly) access specifier, to expose member within class, to other classes within your (same) package. In these other classes (within same package), you can access these default members on instance of Class1. Also you can access these default members within subclasses of Class1, say Class2 (on this reference or on instance of Class1 or on instance of Class2).
Basically, within same package you can access default members on instance of class directly or on 'this' reference in subclasses.
protected:
This access specifier will provide access specified by package-private access specifier in addition to access described below.
When you are developing some package and hence some class (say Class1) within it, then you should use protected access specifier for data member within Class1 if you don't want this member to be accessed outside your package (say in package of consumer of your package i.e. client who is using your APIs) in general, but you want to make an exception and allow access to this member only if client writes class say Class2 that extends Class1. So, in general, protected members will be accessible on 'this' reference in derived classes i.e. Class2 and also on explicit instances of Class2.
Please note:
You won't be able to access inherited protected member of Class1 in
Class2, if you attempt to access it on explicit instance of Class1,
although it is inherited in it.
When you write another class Class3 within same/different package
that extends Class2, protected member from Class1 will be accessible
on this reference and also on explicit instance of Class3. This will
be true for any hierarchy that is extended i.e. protected member
will still be accessible on this reference or instance of extended
class. Note that in Class3, if you create instance of Class2 then
you will not be able to access protected member from Class1 though
it is inherited.
So bottom line is, protected members can be accessed in other packages, only if some class from this other package, extends class enclosing this protected member and protected member is accessed on 'this' reference or explicit instances of extended class, within definition of extended class.
public: This access specifier will provide access specified by protected access specifier in addition to access described below.
When you are developing some package and hence some class (say Class1) within it, then you should use public access specifier for data member within Class1 if you want this member to be accessible in other packages on instance of Class1 created in some class of other package. Basically this access specifier should be used when you intent to expose your data member to world without any condition.
and why the same, can be used with inner classes?
public class Hello {
class inner{ // this class can use any modifier
}
}
Java only allows top level classes / interfaces to be public or package.
Section 7.6 of the JLS states (Top Level Type Declarations):
By default, the top level types declared in a package are accessible
only within the compilation units of that package, but a type may be
declared to be public to grant access to the type from code in other
packages (§6.6, §8.1.1, §9.1.1).
Section 9.1.1 of the JLS of interface modifiers states:
The access modifiers protected and private pertain only to member
interfaces within a directly enclosing class or enum declaration
(§8.5.1).
The modifier static pertains only to member interfaces (§8.5.1, §9.5),
not to top level interfaces (§7.6).
I hope this is clear.
Nested classes can be static, private, protected, package-local, or public
Top level classes are not;
static as this wouldn't mean anything. static for a nest class means it doesn't hold a reference to an outer class, but if you are the outer class it doesn't have a use.
private classes cannot be access from another class file, so a private top level class couldn't be accessed.
protected classes could potentially be used from sub classes, but making the class abstract is clearer. IMHO.
Private top-level class does not make any sense because you can't access it from anywhere.
Protected means to access class within the same package or subclass of the outer class.Since there isn't package inheritance in java then protected classes also does not make any sense.
When we declare method/parameter as static, then we can access it without creating an instance of object.Because static member belongs to the class as a whole, not the instance of class or object. Since there isn't enclosing class for top-level classes, it is meaningless to define top-level classes as static.
All types of access modifiers can be used on all types of classs (except anonymous classes).
Classes with other types of modifiers, will give access, exactly like a method.
static won't work, since it means that it belongs to some other class, that is never true for an outer class.
I have an abstract class which looks like:
abstract class AbstractFoo implements Bar {
//Code goes here
}
However when I try to make AbstractFoo protected I get an error compile time error complaining that it is an illegal modifier.
protected abstract class AbstractFoo implements Bar {
//Code goes here
}
Why can't you have a protected abstract class within Java?
EDIT: I should probably mention that this is not vanilla Java and is actually Blackberry / J2ME.
As many others have noted, the restriction here has nothing to do with the fact that your class is abstract, but rather in the visibility modifier you have chosen to use. Keep in mind what each of these visibility modifiers means:
For the class in which you are using the keyword...
private: Only visible to this class
(default/package private): Only visible to this class and classes in its package
protected: Visible to this class, classes in its package, and subclasses of this class
public: Visible to any class
Top level classes cannot be declared private, because then nothing would ever be able to access them.
But your question stems around why they may not be declared protected. It is clear that a protected top-level class (were it able to exist) would be visible to itself (every class is visible to itself). It is also clear that a protected top-level class would be visible to classes in its package. However, making it visible to its subclasses is tricky. Which classes should be allowed to inherit our protected class?
If it is all of them, then our class might as well be public, because then we're saying that any class has the right to access our protected class. If it's none of them, then our class might as well be package-private, since only the other two conditions (being visible to itself and things in its package) are met. And it can't be "some of them," since we would need a way of defining which classes can access it, which is what the visibility modifier was for in the first place.
So for these reasons, top-level classes cannot be private or protected; they must be package-private or public.
Top level classes can only be public or package-private (default).
public class PublicClass {
protected class InnerClass { } //protected makes sense here
}
class PackagePrivateClass { }
Since: PublicClass and PackagePrivateClass are both top-level classes here they cannot have other access-modifiers, private and protected.
Only the public and the default access-modifiers are allowed for the top-level classes.
But for the inner member classes other modifiers are also allowed.
That abstract has nothing do here most probably.
You can; the following code compiles fine:
public class Main {
interface Bar {}
protected abstract class AbstractFoo implements Bar {}
public static void main(String[] args) {}
}
I do not believe the premise of the question. I successfully compiled the below code:
class prot
{
public abstract class pubab
{
}
protected abstract class protab
{
}
abstract class packprivab
{
}
private abstract class privab
{
}
}
which suggests to me you can have a protected abstract class in java. For that matter you can have a private abstract class.
Did you try to have a protected top-level class (not allowed)?
IMO, it does seem like an illegal modifier because protected means it should be visible in the package + in the derived classes. But in order to declare that some class extends this protected class you first need to be able to see it from there, which can't happen because it's visible only from the derived classes(given that super class and subclasses aren't in the same package).
If you only want to be able to see the class from other classes in the same package the default(package-private) modifier will work, no reason for the protected modifier to work - it only adds a completely unlogical and useless ability to see the class from its derived classes, which
a) can't happen if this class and its derived classes aren't in the same package.
b) can happen, given that this class and its derived classes are in the same package - this will work with the default (package-private) modifier anyway.
Top level classes cannot have protected scope, only public or package. Here's a nice reference explaining the allowable uses of scoping modifiers on classes.
I am not able to understand why this code doesn't compile:
class A {
public static void main(String[] args) {
System.out.println("hi");
}
}
private class B {
int a;
}
I am saving the contents in a file named A.java - and I get an error:
modifier private not allowed here // where I have defined class B
This happens both when I try B as private and protected. Can someone please explain me the reason behind this?
Thanks !
From the Java Language specification:
The access modifiers protected and private pertain only to member classes within a directly enclosing class declaration
So yes, the private and the protected modifiers are not allowed for top level class declarations.
Top-level classes may be public or not, while private and protected are not allowed. If the class is declared public, then it can be referred to from any package. Otherwise it can only be referred to from the same package (namespace).
A private top level class wouldn't make much sense because it couldn't be referred to from any class. It would be unusable by definition. private is OK for member classes to make a class referable to only it's enclosing class.
A protected member class can be referred to from (1) any class of the same package and from (2) any subclass of the enclosing class. Mapping this concept to top level classes is difficult. The first case is covered by top level class with no access modifiers. The second case is not applicable for top level classes, because there is no enclosing class or something else from a different package with a special relation to this class (like a subclass). Because of this I think, protected is not allowed because it's underlying concept is not applicable for top level classes.
Make the B nested of A, like this:
class A {
public static void main(String[] args) {
System.out.println("hi");
}
private class B {
int a;
}
}
Or move B to a separate file. Also you can stick with default access level,
this way the class can be accessed only from within the package:
class A {
public static void main(String[] args) {
System.out.println("hi");
}
}
class B {
int a;
}
private and protected are meaningless to be allowed to a top level(not member) class/interface.
They are applicable only to the class members which can be variables, constants, constructors, methods, classes, and interfaces.
Why:
(1) private: What may be the meaning/purpose if we define a class as private. Its scope should be private to some area. default access is already package private. And nobody wants a class to be source file private, (Guessing the reason) it may not be a good programming practice to allow because java applications are finally organized in the form of packages, but not in terms of source files. Any source file should be part of some package, so in broad/final view each class/interface is part of some package, not just of some .java file. So not applicable.
(2) protected: If something is protected it should be available only within package and only to the sub classes in other packages. To extend a class in a different package, it should be available to all the classes in other packages, but protected says class should be available only to the classes extended it. It's a kind of deadlock situation. So not applicable.
Source: My readings and understanding
Just have no private/protected modifier at all.
B needs to be private to something. Place it within the definition of class A or create another file, B.java, and define it there, but then it cannot be private.
If you don't use the public keyword for the class it will be private by default (visible only within the file).
There can be only one public class per .java file, all the others need to be private. So class A can be public and class B doesn't need any modifiers in your example. The public class name must match the .java file name (eg. A.java can only contain one public class called "A").
A.java cannot contain two classes.