[HN Gopher] JEP 445: Flexible Main Methods and Anonymous Main Cl...
___________________________________________________________________
JEP 445: Flexible Main Methods and Anonymous Main Classes (Preview)
Author : mfiguiere
Score : 44 points
Date : 2023-04-10 17:41 UTC (5 hours ago)
(HTM) web link (openjdk.org)
(TXT) w3m dump (openjdk.org)
| hyperpape wrote:
| Question that just now occurs to me: what if you have the follow
| class and invoke it? (typing without an IDE, forgive any
| compilation errors). I can imagine answers, but I'm not sure if
| the JEP explains which one will happen (genuinely unsure, I
| could've easily missed it).
|
| public class Foo { int x; public
| Foo(int x) { this.x = x; }
| void main() { System.out.println(x); } }
| pron wrote:
| The JEP says:
|
| > If a launched class has no static main method but has a non-
| private zero-parameter constructor ... and a non-private
| instance main method, then construct an instance of the
| class... [and] invoke the instance main method
|
| Your class doesn't have a zero-parameter constructor nor a
| suitable static main, so launching it as a program will fail
| (as it would today).
| johnfn wrote:
| Pretty nice! Makes me wonder why they didn't take the final step
| and say that anything not inside `void main()` gets bundled up
| into an implicit function run first.
| djur wrote:
| It's addressed near the end:
|
| > Eliminating the main method altogether may seem like the
| natural next step, but it would work against the goal of
| gracefully evolving a first Java program to a larger one and
| would impose some non-obvious restrictions (see below):
|
| The "see below" boils down to there being a number of
| differences between how class-level and method-level code units
| (fields vs. variables) work, and blurring the line there isn't
| worth the minor additional effort of writing a main() method.
| specialist wrote:
| Love it.
|
| Don't forget to support shebang. So we can finally use Java as a
| system scripting language.
|
| Maybe something like: #!/usr/bin/env java
|
| And maybe also allow specifying the runtime version:
| #!/usr/bin/env java-12.0.*
| carimura wrote:
| Like this? https://dev.java/learn/single-file-program/
| mfiguiere wrote:
| The timeline of its promotion from draft status along with
| several mentions of JDK 21 in the provided examples make it
| likely to ship with JDK 21 in September.
| kasperni wrote:
| As a preview feature
| yarg wrote:
| All I can think coming away from this is:
|
| This still seems pretty useless, It'd be nice if java could allow
| for static interface methods. interface Program
| { static void main(String...args); }
|
| And then I digressed - heavily.
|
| There have been several times when I've wanted static methods
| that apply to the specific class - although many of the
| situations could be shoehorned into a constructor, it's not the
| best.
|
| You'd also want something like a 'This' meta-class keyword.
| interface Foo extends Comparable<This> { static
| This(A argA, B argB); static This
| difference(This v0, This v1); static int
| compare(This v0, This v1); default int
| compareTo(This other){ return compare(v0, v1);
| } } /* I want to return an
| instance of my class' own type (defined in a subclass an so
| unknown), so I pass every implementation itself as
| its own generic parameter. */ interface
| Why<W extends Why<W>> implements Comparable<W>{ W
| someManipulation(); } class Foo implements
| Why<Foo> { @Override Foo
| someManipulation(){ .... } }
|
| To be honest, I think I reacted to how robust this does not feel.
|
| It also blurs the line between static and instance
| syntax/functionality in a way that does not seem useful - and
| given that this is intended to reduce barriers to entry, is quite
| probably harmfully confusing.
| yarg wrote:
| A better example of what I'm thinking:
| interface Number { static This sum(This v0, This
| v1); static This difference(This v0, This v1);
| static This product(This v0, This v1); static This
| quotient(This v0, This v1); } void <N
| extends Number> doThings(N v0, N v1){ N sum =
| N.sum(v0, v1); }
| tpoacher wrote:
| My 2C/ is that this will probably do more to confuse than to
| enlighten students.
|
| Getting your "first" program off the ground quickly is good, but
| only if it doesn't cripple your understanding of what's going on
| for months later.
|
| For me the main thing that confuses the crap out of students is
| how people who introduce java tend to take "shortcuts" and bundle
| all functionality under the sun into a single class, which then
| also has a main method at the end. Presumably this is done so
| that everything is a single file, or can fit in a single
| presentation slide. But then suddenly your main looks like it's
| calling its container class to make objects of "itself" that
| contain new "mains", at which point your student has lost the
| plot completely.
|
| The simplest thing to keep things clean and self explanatory is
| to separate everything that isn't "main-related" into its own
| class (preferably another file if public), and then keep a nice
| clean public class called "Main" which contains 'only' the main
| method. Then you get to explain nicely how public classes have
| their own files, and if you attempt to run this class from the
| terminal, java will look for the 'main' function, and how this
| therefore needs to be public, static because you're running it
| straight from the class, void because you don't depend on it
| returning a value (which also makes for a nice intermission on
| how c returns status as an int, but java has a special mechanism
| instead).
|
| I do agree with the end of the JEP though; if you want to teach
| simple snippets like System.out.println, jshell is a nice way to
| do this, if you want to delay talking about classes and their
| methods.
| WhereIsTheTruth wrote:
| Kotlin and the likes proved them wrong
|
| Glad to see them evolving faster as a result
| clhodapp wrote:
| I'd love to see them follow with full-blown package-level methods
| and fields at some point (as alluded to in the alternatives) but
| this seems like a great minimal change to address a real pain
| point with learning to code in Java.
| hyperpape wrote:
| The section on how the main method will be resolved is a bit
| painful. I can't see a way around it that doesn't do nasty things
| for composability and/or backwards compatibility, but it does
| give me pause. Any situation where you have to ask "which main
| method in this class will be executed?" is quite bad.
| pgwhalen wrote:
| As much as it's a crutch in programming language design to say
| "we don't have to worry too much about the lack of ergonomics
| in this case, it would be such bad code if this edge case gets
| run into in the first place," this seems like one of those
| situations.
|
| Another point: IDEs will be able to tell you which main method
| will get chosen, which should eliminate at least some
| uncertainty.
| pron wrote:
| Which is why, as part of designing this feature, we ran a
| corpus search to see what portion of classes with a main method
| have another main that would be a candidate entry point under
| this JEP. It was negligible. Additionally, we'll give a linter
| warning if there's more than one candidate.
| java-man wrote:
| I feel like this is introducing a change for the sake of change,
| solving a problem which does not exist. The price of this change
| is very real: adding complexity and bugs to all the tools, IDEs,
| code analyzers and the like.
|
| There is negative net benefit to pretty much everyone involved,
| and for what?
| justin_oaks wrote:
| I do wonder how much benefit will be gained from this. Is the
| main method really causing beginners that many problems?
|
| I'd say beginners are much more likely to trip over other
| problems with the language like using == with String instances,
| the differences between primitives and objects (e.g. copy-by-
| value vs copy-by-reference, no methods on a primitive, etc.),
| or the unending problems with null.
|
| Of course, those may never be resolved, and so we'll have to
| change something that doesn't really matter instead.
| crummy wrote:
| Not sure if you're being sarcastic but the solution to some
| of those things is on the horizon (e.g. null awareness).
| Seems like a lot of work is necessary to get there though.
| Pet_Ant wrote:
| That is literally what is addressed by the first section of the
| document. Both in "Summary" and in "Goals"
|
| > Far from using a separate dialect of Java, students can write
| streamlined declarations for single-class programs and then
| seamlessly expand their programs to use more advanced features
| as their skills grow.
|
| I remember when I started with Java 20 years we had a special
| IDE (BlueJ maybe? DrJava?) that wrapped the main class so that
| <code>System.out.println("Hello world");</code> was a complete
| program.
|
| So that is clearly
|
| > Do not introduce a separate beginner's dialect of Java.
|
| Perhaps this is in response to Python growing as an initial
| programming language (IMHO wrongly because types are
| fundamental to thinking about programming).
|
| They also mention:
|
| > Reduce the ceremony of writing simple programs such as
| scripts and command-line utilities.
|
| You can question the merits or trade-offs, but it's very
| clearly spelled out.
|
| > Reduce the ceremony of writing simple programs such as
| scripts and command-line utilities.
| java-man wrote:
| Is this really what students struggle with?
|
| I think it is important to be able to determine the root
| cause of a problem first. Do students find difficult to write
| "public static void main(String[] args)" or do they find
| difficulty understanding the concepts of a public method, a
| static method, a void method? Perhaps then we should focus on
| teaching these concepts, which are essential to java, first,
| instead of undermining the core of the language and the
| platform.
|
| Neither "goals" nor "summary" can explain away why this can
| solve the problem this JEP purports to solve.
|
| This is my opinion, of course.
| OkayPhysicist wrote:
| The problem is when you sit down to teach the beginner, all
| the boilerplate clutter forces you to either A) teach them
| the magic incantation to be unquestionably written before
| they start writing any code, or B) you explain everything
| before getting into any real programming.
|
| Both suck. In the first case, students are torn away from
| the mode of thinking that programming thrives in: that
| everything is made up of simple, understandable pieces,
| that can be built up into complex solutions. It ends up
| serving as a trap for the very kind of inquisitive student
| that is equipped to succeed in programming. In the second
| case, everyone's bored to tears, and you can be assured
| that your entire class will be hopelessly lost before they
| write their first line of code. It's a bad time all around.
|
| Basically, programming wants to be built up with the
| following concepts, in order:
|
| 1. Algorithmic Thinking (solutions can be representing as a
| series of simple steps)
|
| 2. Structured Syntax (these steps can be represented as
| structured text)
|
| 3. Symbolic Reasoning (types, variables, arrays)
|
| 4. Control Flow (loops, conditionals)
|
| 5. Functions
|
| 6. Higher Structures (classes, objects, etc)
|
| Python, IMO, is pretty good pedagogical tool in this regard
| print("Hello World")
|
| "We want our computer to display to us (or 'print' in
| software terms) the phrase 'Hello World'. Python provides
| us with a built-in way to do so: the "print" function. In
| the majority of programming languages, we express a call to
| a function as a command, followed by its inputs (or
| 'arguments') contained within parentheses. As our one and
| only argument, we provide what we want printed, in this
| case the text "Hello World". By wrapping this text in
| quotes, we can tell the language that we intend this text
| to be interpreted as a chunk of literal text, called a
| 'String' rather than as a variable or other symbol for the
| language."
|
| In contrast, explaining everything going on in the
| equivalent Java public class MyFirstClass
| { public static void main(String[] args){
| System.out.println("Hello World"); } }
|
| would take more text than I'm willing to hammer into a HN
| comment, but to be explained to a complete beginner would
| likely involve skipping, but promising to explain later:
| classes, functions, "public", "static", "void", command
| line arguments, and the uniquely weird "System.out",
| followed by a similar explanation to the Python example,
| with the added "we end each step with a semicolon".
| java-man wrote:
| Thank you for a detailed explanation!
|
| Please see my response to @pgwhalen. In short, the
| problem has, I think, a much simpler solution.
|
| What I really dislike about this JEP is not only that it
| tries to solve the educational problem in a worst
| possible manner (my opinion), but it also risks creating
| a generation of students who don't really understand the
| fundamental concepts that allow us to write reliable
| code.
|
| Perhaps we need to start teaching basic programming with
| BASIC instead, and graduate to a more complicated
| platform once the basic concepts have been understood.
| OkayPhysicist wrote:
| My personal opinion on it is that Java's simply a bad
| first language, and over-taught in schools. It has a lot
| of language-specific baggage that it thrusts upon you
| immediately on first use. My preferred first (university-
| level) language is Racket, because it's got incredibly
| simple syntax as a LISP, it's radically batteries-
| included giving a good sandbox to play in, and segues
| into CS-theory type stuff pretty damn well. It also has
| the added bonus of minimizing the impact on the subset of
| the class with non-trivial programming experience, who
| otherwise can easily get bored hearing stuff they know
| already, stop paying attention because they assume they
| know everything already, and then wash out when the real
| CS-heavy stuff hits.
|
| But a lot of "universities" treat their "CS" programs as
| glorified trade schools, and want to focus exclusively on
| industry-applicable languages, and land on Java because
| Oracle had a great outreach program. Like it or not, many
| students will be starting their programming journey in
| Java, and not fucking it up is probably a good idea.
|
| My approach would have been pretty similar to their
| listed alternative under "Interpret code units as static
| members", but that probably comes down to differences
| over the importance of Object-Oriented principals in
| beginner programming pedagogy.
|
| Barring that, this proposal really isn't bad. It doesn't
| break existing code, it does its job well enough. I would
| have liked there to be support for inline subclasses that
| can be called from within the same anonymous class
| environment, but I can see how that would create
| ambiguity with existing code.
| pron wrote:
| > Perhaps then we should focus on teaching these concepts,
| which are essential to java, first.
|
| As the JEP explains, this change does make the concepts of
| classes and access modifiers easier to teach by allowing
| the teacher to postpone their introduction to a point in
| time when they're actually useful and can be understood.
| Access control, static, and class declarations are only
| meaningful once you have _other_ classes and /or objects
| interacting with your code. We don't want to force teachers
| to teach programming in the large early because many of
| them told us they don't do that anyway.
|
| > instead of undermining the core of the language and the
| platform
|
| The syntax and concepts of anonymous classes are unchanged.
| Providing an unnamed class, implicitly, when a class isn't
| needed is consistent with how we already provide an unnamed
| package and an unnamed module implicitly when they're not
| needed.
| pgwhalen wrote:
| It sounds like you haven't taught or taken an intro to
| programming course using Java before.
|
| In that situation, instructors might spend weeks trying to
| get their students to understand variables or control flow
| concepts. Visibility may be a core concern for you, as a
| (presumably) professional Java programmer, but it's not at
| all to programming novices.
| java-man wrote:
| This particular problem, in my opinion, has a much
| simpler solution: a special educational environment. A
| sort of mini-IDE where two things happen:
|
| 1. code written by a student gets inserted into a top-
| level class's main() method (has to be smart enough to
| deal with imports, inner classes etc.)
|
| 2. the top level class might declar certain utility
| functions such as print() instead of
| System.out.println(), and possibly others.
|
| Bingo. No need to mess with something that works just
| fine for 99.99% of the professional users.
|
| edit, in response to @crummy (as we reached the maximum
| depth it seems):
|
| Some people commented that it might be beneficial to
| delay introduction of more complex concepts until the
| basic ones are digested. So hiding the class/main method
| would help with that (similar to jshell, I might add).
| And keep in mid this is an IDE and not java-lite.
| crummy wrote:
| In your other comment you said:
|
| > What I really dislike about this JEP is not only that
| it tries to solve the educational problem in a worst
| possible manner (my opinion), but it also risks creating
| a generation of students who don't really understand the
| fundamental concepts that allow us to write reliable
| code.
|
| How would your special IDE/forked Java-lite prevent
| creating a generation of students who don't really
| understand the fundamental concepts that allow us to
| write reliable code?
| djur wrote:
| Such an environment already exists, and the JEP rejects
| it as an option:
|
| > Evolving a batch of working declarations in JShell into
| a real Java program leads to a non-idiomatic style of
| code because it declares each method, class, and variable
| as static... it is not the on-ramp programming model we
| are looking for.
| easton wrote:
| Why would this cause extreme problems for Java where it didn't
| for C# doing the same thing a few years ago? I'm honestly
| asking not having done Java in a few years, as I remember they
| both had this "you gotta put all the code in classes" problem.
| ht_th wrote:
| In my experience teaching introductory programming with Java,
| the problem is very real. For beginning programmers, making
| sense of the first Java program(s) results too often in
| misunderstanding of all sorts of concepts.
|
| Of course, you can tell students to ignore most of the code
| until later in the course when they'll learn all about it, but
| that doesn't work. They'll make sense of the code within their
| limited understanding of programming and frames of reference.
| They'll build local theories of how and why these programming
| elements, like "static", "class", "main", "String[]" etc. fit
| together, how they relate to error messages they get when their
| programs don't compile or don't work.
|
| Then, when they do reach the place in the course when they're
| to learn all about these concepts, they have to reconcile their
| own local theories with the material at hand to create a more
| thorough and evolved understanding of the concept. That's often
| not an easy process. In many introductory programming courses,
| there's not much time for reflection. As a result, their
| evolving understanding is likely closer to their initial
| understanding instead of the ones we aim at as teachers.
|
| What's not helping here is that as experienced programmers who
| have developed a deep understanding of these concepts to
| understand novice's point-of-view and their struggles with the
| material.
|
| Learning and teaching is hard!
| justin_oaks wrote:
| Thanks for explaining the problem. Do you think the proposed
| changes will help significantly and will be worth the
| trouble?
| [deleted]
| smarks wrote:
| Thanks for raising this issue. What you describe as "local
| theories" (I'd say "mental model" but I think we're talking
| about the same thing) is quite important. We expect beginners
| to come up with erroneous models as they're exposed to stuff;
| revising and even discarding such models is intrinsic to
| learning. One of the benefits of this JEP is to minimize the
| opportunities for beginners to create erroneous mental
| models.
| slaymaker1907 wrote:
| I've written a ton of Java and I'd find this handy for datetime
| stuff. Even though I don't use it for my work anymore, I still
| pull out Java when I need to answer questions like what day is
| 90 days from now because java.time.* is very well designed.
| Instead of just using the shell, this makes things a little
| nicer with less ceremony if I want to do these date
| calculations in a local file.
___________________________________________________________________
(page generated 2023-04-10 23:01 UTC)