6

Obviously Java has a Access level package-private which achieved by not adding any explicit modifier.

But isn't there a way to explicitly add this modifier? It's a bit confusing that we need to omit access level when we want to use member in package only.

If there's no way, why package private decided to be a default level?

For example if default level was public than we would more consciously define relevant access level.

This isn't duplicate of question of why use it, because I know why, I just don't know why it's define implicitly and can't be defined explicitly.

EDIT

You can define it explicitly by using Lombok's @PackagePrivate

Used to indicate the explicit intention for the annotated entity to have the package private access level. Currently used by FieldDefaults and Value to avoid having it make a field one of public, protected, or private.

@PackagePrivate String thanksLombok;
Ori Marko
  • 56,308
  • 23
  • 131
  • 233
  • 6
    Why? Because that's how they designed the language, wayyy back when. – Andreas Oct 03 '18 at 05:22
  • @Andreas Why not providing this very specific case of level got to be the default and can't be defined explicitly? E.g. If default was public than we would more consciously define relevant access level – Ori Marko Oct 03 '18 at 05:25
  • *But isn't there a way to explicitly add this modifier?* I guess `no explicit modifier` means `no` – Scary Wombat Oct 03 '18 at 05:25
  • 2
    @user7294900 *"If default was `public` than we would more consciously define relevant access level"* I don't follow. Why would a default of `public` do that? You always have to *consciously* decide on access level, by either writing a keyword, or not. Not writing a keyword is still a *conscious* decision. – Andreas Oct 03 '18 at 05:29
  • Why? I guess because putting stuff inside a folder (package) should mean that I want them to be accessible by default. `protected` is similar but it will leak access to sub-classes in other packages. I too would have chosen package-private to be the default because of this reason. – Kartik Oct 03 '18 at 05:29
  • @Kartik so you are saying it's access based on physical directory and not code? – Ori Marko Oct 03 '18 at 05:32
  • 1
    @user7294900 package-private means accessible to the package, and a package is nothing but a directory in the operating system.. so if access is based on package, it implies access is based on physical directory, yes – Kartik Oct 03 '18 at 05:34
  • @Andreas I think not writing something is not always a conscious decision, specially for new comers – Ori Marko Oct 03 '18 at 05:34
  • Possible duplicate of [Java default access level (package private access). Why it is used for?](https://stackoverflow.com/questions/28414803/java-default-access-level-package-private-access-why-it-is-used-for) – S.K. Oct 03 '18 at 05:35
  • @user7294900 If you feel that not writing something is not always a conscious decision: Since all code within a package is in an implicit *trust relationship*, the default of allowing cross-class access *within* the package makes sense. Granting extra access should be a *conscious* decision, made after considering all the implications, so a default of `public` is certainly wrong. – Andreas Oct 03 '18 at 05:36
  • @Kartik I think your comment can be an answer if you want – Ori Marko Oct 03 '18 at 05:39
  • 1
    I have a @package_local annotation when I want to make it clear I intended to make a member package local rather than I forgot to define it. – Peter Lawrey Oct 03 '18 at 06:52
  • @PeterLawrey It's just a Tag/marker interface? – Ori Marko Oct 03 '18 at 08:35
  • @PeterLawrey guava has one such too `@VisibleForTesting`, a little different purpose, but the idea is around that too – Eugene Oct 03 '18 at 09:16

2 Answers2

1

In my opinion,

It would be bad if the default was

public because you could miss specifying the modifier and the piece of code that was intended to be private or something would be accessible to the world. Also, this might be against one of the OOP's core concepts - encapsulation.

private because generally you would want to interact with other classes instead of writing everything in one class.

protected because I would expect (personal opinion) things that are in a folder (package) to be accessible inside the folder and not in a class (child class) residing in some completely different directory.


If I were to do it again, I would choose package-private as the default because if some things are together (in the same package), the intention might be that they should be able to talk to each other.

Kartik
  • 7,677
  • 4
  • 28
  • 50
  • 1
    Just a comment, in `interface` no modifier is implicitly `public` ,which can create confusion – Ori Marko Oct 08 '18 at 10:59
  • 1
    I do not agree with your reasoning for a `private` default being bad. Defaulting to the most restrictive option generally makes sense. If you ever do try to access it from outside the class you will immediately get a compiler error and see that you need to relax the access. And if you never try to, then `private` was the correct choice. Whereas if you intended it to be private, but accidentally left it package private, you may never notice that you've left it less restrictive than intended. – Sean Burton May 15 '20 at 14:39
  • @SeanBurton Valid point. So the choice is between what you said, and package-private. I would still choose package-private and _risk_ my members being visible to others in the same package. After all if it's in the same package, the code is under my control and there is not a huge benefit in blocking access when I can go ahead and change access any time. Writing the keyword `protected` all the time even when I am talking to my own code within the same package, might be annoying. Again, we might not agree, but that's ok as the question is marked as _opinion-based_. – Kartik May 18 '20 at 08:19
1

But isn't there a way to explicitly add this modifier?

No there isn't. (Short of modifying the Java language, which is highly unlikely for something like this.)

The rest of your question calls for opinion-based answers1 and is off topic.


1 - 1) We were not in the room ~25 years ago when the design decisions were made. 2) There is (AFAIK) no extant publicly available documentation for the original language design decisions. 3) The people who were in the room will have probably mostly forgotten, even if we could ask them. 4) Any attempt by your / me to "reverse engineer" the original thinking will be colored by ~25 years of hindsight.

Stephen C
  • 698,415
  • 94
  • 811
  • 1,216