From gavin.bierman at oracle.com Fri Apr 7 21:28:32 2023 From: gavin.bierman at oracle.com (Gavin Bierman) Date: Fri, 7 Apr 2023 21:28:32 +0000 Subject: Draft Spec for Pattern Matching for switch (JEP 441) and Record Patterns (JEP 440) now available Message-ID: <74893015-FD27-44AA-84FD-375BC240DF89@oracle.com> Dear experts: The first draft of the joint spec change document for the features Pattern Matching for switch [1] and Record Patterns [2] is now available at: https://cr.openjdk.org/~gbierman/jep440+441/latest/ Please give us your feedback (either on this list or directly to me). Thanks, Gavin [1] Pattern matching for switch: https://openjdk.org/jeps/441 [2] Record patterns: https://openjdk.org/jeps/440 From forax at univ-mlv.fr Tue Apr 11 18:32:24 2023 From: forax at univ-mlv.fr (Remi Forax) Date: Tue, 11 Apr 2023 20:32:24 +0200 (CEST) Subject: Revisit the String template syntax In-Reply-To: References: Message-ID: <786405814.34388890.1681237944261.JavaMail.zimbra@univ-eiffel.fr> I've promoted this email to amber-spec-experts given that several people on the internet and offline have said more or less the same thing. Even if it's not for 21, now that a string template is always prefixed by a template processor, the part in between quote does not need to rely on backslash '\' anymore. Should we still keep the current syntax \{...} or should we go to the more usual ${...} syntax ? regards, R?mi ----- Original Message ----- > From: "Octavia Togami" > To: "amber-spec-comments" > Sent: Tuesday, April 11, 2023 1:39:20 AM > Subject: Syntax question for JEP 430: String Templates > Hi, > > I was reading this portion of the alternatives section: > >> For the syntax of embedded expressions we considered using ${...}, but that >> would require a tag on string templates (either a prefix or a delimiter other >> than ") to avoid conflicts with legacy code. > > And it seems that this is no longer a valid reason, as per [1] there > is always a required prefix anyways. Is there another reason to avoid > using this syntax now? > > Thanks, > Octavia > > [1]: > https://mail.openjdk.org/pipermail/amber-spec-experts/2022-October/003631.html From james.laskey at oracle.com Tue Apr 11 18:35:43 2023 From: james.laskey at oracle.com (Jim Laskey) Date: Tue, 11 Apr 2023 18:35:43 +0000 Subject: Fwd: Syntax question for JEP 430: String Templates References: <8EECB110-59D5-49BC-A812-1E870CCA4E90@oracle.com> Message-ID: <6FDD31DF-9CB7-422E-8854-95CAB74B905F@oracle.com> Begin forwarded message: From: Jim Laskey Subject: Re: Syntax question for JEP 430: String Templates Date: April 11, 2023 at 1:11:58 PM ADT To: Octavia Togami Cc: amber-spec-comments at openjdk.org Octavia, I?m assuming you want ${?} used because that?s what many other languages use (if that is not the reason, apologies). I would argue that it is an advantage for Java not to use what other languages use. More on that toward the end of this reply. JEP 430 indicates why \{?} was chosen and I don?t think the reasoning is weakened by the processor expression prefix requirement. - Backslash was chosen because the combination of \{ would not create compatibility issues with older Java source. - Braces were chosen because it is less likely that braces would be used in an embedded expression (versus parentheses and brackets). Note that Swift uses \(?). Using ${?} to indicate embedded expressions would create two distinct categories of quoted elements, that is, ${?} would be lexically different for strings versus templates. Sounds simple, but tools wouldn't know which way to tokenize the quoted element until the tool?s grammar detected the "processor dot template" context (and note that processor can be a complex expression). Since most tools separate scanning (lexicon, tokens) from parsing (grammar) this forces the tooling to provide some sort of feedback between the lexicon and grammar ? gets messy. Using \(?) makes it easy for javac to tokenize both strings and templates without feedback from the parser. Note that you would have to add a new escape sequence for $ if you want to use $ in the template.) Other languages can support ${?} at the lexicon level because their strings were designed to support ${?} from the beginning or have simple ways to indicate that the quoted element needs to be treated differently ? different quotes, tag prefix, ? . Back to what I stated at the beginning, I think that \{?} is an advantage for string templates in much the same way that triple quotes works for text blocks, \{?} doesn?t conflict with other languages. Java serves a polyglot universe, where it is not uncommon to embed other language source in a Java app. For example; Object result = JAVASCRIPT.""" let header = "Templates Literals"; let tags = ["template literals", "javascript", "es6"]; let html = `

${header}

    `; for (const x of tags) { html += `
  • ${x}
  • `; } html += `
`; """; or Object result = BASH.""" Recipient=?admin at example.com? Subject=?Greeting? Message=?Welcome to our site? `mail -s ${Subject} ${Recipient} <<< ${Message}` """; Though you would not have the advantage of embedded expressions, it is also possible to use ${?} for your own style of template. We assume existing template libraries will provide similar StringTemplate ?bridging". static final StringTemplate.Processor MY_STYLE = st -> { String text = st.interpolate(); Pattern p = Pattern.compile("\\$\\{(.*?)\\}"); Matcher m = p.matcher(text); List fragments = new ArrayList<>(); List values = new ArrayList<>(); int last = 0; while (m.find()) { fragments.add(text.substring(last, m.start())); values.add(m.group(1)); last = m.end(); } fragments.add(text.substring(last)); return StringTemplate.of(fragments, values); }; public static void main(String[] args) { StringTemplate mailer = MY_STYLE.""" Dear ${name}, This is to inform you that your ${package} will be delivered on ${date}. Respectfully, Big Shop """; Map data = Map.of( "name", "Joan", "package", "bicycle", "date", "May 31" ); System.out.println(StringTemplate.interpolate( mailer.fragments(), mailer.values().stream().map(data::get).toList() )); } ----------------------------------------------------- Dear Joan, This is to inform you that your bicycle will be delivered on May 31. Respectfully, Big Shop ----------------------------------------------------- Hope this frames a better understanding. Cheers, ? Jim -------------- next part -------------- An HTML attachment was scrubbed... URL: From forax at univ-mlv.fr Tue Apr 11 18:48:03 2023 From: forax at univ-mlv.fr (Remi Forax) Date: Tue, 11 Apr 2023 20:48:03 +0200 (CEST) Subject: Named record patterns In-Reply-To: References: Message-ID: <1657524168.34391795.1681238883293.JavaMail.zimbra@univ-eiffel.fr> > From: "Robbe Pincket" > To: "amber-dev" > Sent: Monday, April 10, 2023 1:27:22 PM > Subject: Named record patterns > Hi all > I was wondering if named record patterns `o instanceof Pair(String left, String > right) pair` are still on the table for the future or not. (Not sure if 'named' > record pattern is the right name?) Let re-state what is the issue, currently there is no way to create a binding capturing the whole record instance, forcing people to transform the record pattern to a type pattern + when (see below). A previous preview was supporting this case using the syntax case Pair(String left, String right) pair -> ... which did not work well in case someone want the binding to be also have an annotation or be declared final Here is the previous syntax with "final" case final Pair(String left, String right) pair -> ... which is not very readable, the "final" being too far apart from the binding. One solution is to use a keyword like "as" to add a binding at the end of a record pattern (and perhaps other patterns ?) case Pair(String left, String right) as final pair -> ... which as the advantage of grouping the binding and its keyword at the cost of adding a new keyword. R?mi > IIRC they were shelfed due to the ambiguity that they could cause in this case, > if there also exists a function `when`: > ``` > switch(o) { > case Pair(String left, String right) when when (left == right) -> ... > } > ``` > It feels weird to me however that this feature was shelved just for this case, > when a 'simple' rule could be introduced that a record pattern can't introduce > a pattern variable with the name of a contextual keyword or at least not > `when`. > Are there other reasons that record patterns can't introduce a variable that > matches the whole pair anymore? It feels like it could be useful, even more so > with JEP 443: Unnamed Patterns and Variables (Preview) > ``` > if (o instanceof ColoredPoint(Point(_, int y), _) cp && y > 0) { > doAction(cp); > } > ``` > Instead of > ``` > if (o instanceof ColoredPoint(Point(int x, int y), Color c) && y > 0) { > doAction(new ColoredPoint(new Point(x, y), c)); > } > ``` > or this, if ColoredPoint can both hold `Point` and `Point3D` > ``` > if (o instanceof ColoredPoint cp && cp.point() instanceof Point(_, int y) && y > > 0) { > doAction(cp); > } > ``` > or if it can only hold `Point` > ``` > if (o instanceof ColoredPoint cp && cp.point().y() > 0) { > doAction(cp); > } > ``` > Greetings > Robbe Pincket -------------- next part -------------- An HTML attachment was scrubbed... URL: From amaembo at gmail.com Tue Apr 11 21:12:41 2023 From: amaembo at gmail.com (Tagir Valeev) Date: Wed, 12 Apr 2023 01:12:41 +0400 Subject: Syntax question for JEP 430: String Templates In-Reply-To: <6FDD31DF-9CB7-422E-8854-95CAB74B905F@oracle.com> References: <8EECB110-59D5-49BC-A812-1E870CCA4E90@oracle.com> <6FDD31DF-9CB7-422E-8854-95CAB74B905F@oracle.com> Message-ID: Hello! As we're here, I wonder whether \[...] was considered. I see a big advantage over \{...}, because one doesn't need to hold shift key to type [ in widely used US-qwerty layout (and some other widely used layouts as well). Such character sequence is much easier to type. With best regards, Tagir Valeev On Tue, Apr 11, 2023, 22:36 Jim Laskey wrote: > > > Begin forwarded message: > > *From: *Jim Laskey > *Subject: **Re: Syntax question for JEP 430: String Templates* > *Date: *April 11, 2023 at 1:11:58 PM ADT > *To: *Octavia Togami > *Cc: *amber-spec-comments at openjdk.org > > Octavia, > > > I?m assuming you want ${?} used because that?s what many other languages use (if that is not the reason, apologies). I would argue that it is an advantage for Java not to use what other languages use. More on that toward the end of this reply. > > JEP 430 indicates why \{?} was chosen and I don?t think the reasoning is weakened by the processor expression prefix requirement. > > - Backslash was chosen because the combination of \{ would not create compatibility issues with older Java source. > > - Braces were chosen because it is less likely that braces would be used in an embedded expression (versus parentheses and brackets). Note that Swift uses \(?). > > Using ${?} to indicate embedded expressions would create two distinct categories of quoted elements, that is, ${?} would be lexically different for strings versus templates. Sounds simple, but tools wouldn't know which way to tokenize the quoted element until the tool?s grammar detected the "processor dot template" context (and note that processor can be a complex expression). Since most tools separate scanning (lexicon, tokens) from parsing (grammar) this forces the tooling to provide some sort of feedback between the lexicon and grammar ? gets messy. > > Using \(?) makes it easy for javac to tokenize both strings and templates without feedback from the parser. Note that you would have to add a new escape sequence for $ if you want to use $ in the template.) > > Other languages can support ${?} at the lexicon level because their strings were designed to support ${?} from the beginning or have simple ways to indicate that the quoted element needs to be treated differently ? different quotes, tag prefix, ? . > > Back to what I stated at the beginning, I think that \{?} is an advantage for string templates in much the same way that triple quotes works for text blocks, \{?} doesn?t conflict with other languages. Java serves a polyglot universe, where it is not uncommon to embed other language source in a Java app. For example;Object result = JAVASCRIPT.""" > let header = "Templates Literals"; > let tags = ["template literals", "javascript", "es6"]; > > let html = `

${header}

    `; > for (const x of tags) { > html += `
  • ${x}
  • `; > } > > html += `
`; > """;orObject result = BASH.""" > Recipient=?admin at example.com? > Subject=?Greeting? > Message=?Welcome to our site? > `mail -s ${Subject} ${Recipient} <<< ${Message}` > """; > > Though you would not have the advantage of embedded expressions, it is also possible to use ${?} for your own style of template. We assume existing template libraries will provide similar StringTemplate ?bridging". > > static final StringTemplate.Processor MY_STYLE = st -> { > String text = st.interpolate(); > Pattern p = Pattern.compile("\\$\\{(.*?)\\}"); > Matcher m = p.matcher(text); > List fragments = new ArrayList<>(); > List values = new ArrayList<>(); > int last = 0; > > while (m.find()) { > fragments.add(text.substring(last, m.start())); > values.add(m.group(1)); > last = m.end(); > } > fragments.add(text.substring(last)); > > return StringTemplate.of(fragments, values); > }; > > public static void main(String[] args) { > StringTemplate mailer = MY_STYLE.""" > Dear ${name}, > > This is to inform you that your ${package} will be > delivered on ${date}. > > Respectfully, > > Big Shop > """; > Map data = Map.of( > "name", "Joan", > "package", "bicycle", > "date", "May 31" > ); > System.out.println(StringTemplate.interpolate( > mailer.fragments(), > mailer.values().stream().map(data::get).toList() > )); > } > > ----------------------------------------------------- > > Dear Joan, > > This is to inform you that your bicycle will be > delivered on May 31. > > Respectfully, > > Big Shop > > ----------------------------------------------------- > > Hope this frames a better understanding. > > Cheers, > > ? Jim > > > -------------- next part -------------- An HTML attachment was scrubbed... URL: From james.laskey at oracle.com Tue Apr 11 21:38:21 2023 From: james.laskey at oracle.com (Jim Laskey) Date: Tue, 11 Apr 2023 21:38:21 +0000 Subject: [External] : Re: Syntax question for JEP 430: String Templates In-Reply-To: References: <8EECB110-59D5-49BC-A812-1E870CCA4E90@oracle.com> <6FDD31DF-9CB7-422E-8854-95CAB74B905F@oracle.com> Message-ID: <75656881-FC09-4EA3-BBA1-BDCCBD32E30D@oracle.com> I get that and brace choice is a bit arbitrary but I think indexing would be a fairly frequent use case. You end up with "\[array[i]]". The Swift parentheses "\(array[i])" style is better than brackets because we are use to parenthesizing expressions. But in the end, braces are rarely used in expressions and the braces visually pop the embedded expression "\{array[i]}". I think this is because we are conditioned to think of braces as being outermost bracketing. Cheers, ? Jim ? On Apr 11, 2023, at 6:13 PM, Tagir Valeev wrote: ? Hello! As we're here, I wonder whether \[...] was considered. I see a big advantage over \{...}, because one doesn't need to hold shift key to type [ in widely used US-qwerty layout (and some other widely used layouts as well). Such character sequence is much easier to type. With best regards, Tagir Valeev On Tue, Apr 11, 2023, 22:36 Jim Laskey > wrote: Begin forwarded message: From: Jim Laskey > Subject: Re: Syntax question for JEP 430: String Templates Date: April 11, 2023 at 1:11:58 PM ADT To: Octavia Togami > Cc: amber-spec-comments at openjdk.org Octavia, I?m assuming you want ${?} used because that?s what many other languages use (if that is not the reason, apologies). I would argue that it is an advantage for Java not to use what other languages use. More on that toward the end of this reply. JEP 430 indicates why \{?} was chosen and I don?t think the reasoning is weakened by the processor expression prefix requirement. - Backslash was chosen because the combination of \{ would not create compatibility issues with older Java source. - Braces were chosen because it is less likely that braces would be used in an embedded expression (versus parentheses and brackets). Note that Swift uses \(?). Using ${?} to indicate embedded expressions would create two distinct categories of quoted elements, that is, ${?} would be lexically different for strings versus templates. Sounds simple, but tools wouldn't know which way to tokenize the quoted element until the tool?s grammar detected the "processor dot template" context (and note that processor can be a complex expression). Since most tools separate scanning (lexicon, tokens) from parsing (grammar) this forces the tooling to provide some sort of feedback between the lexicon and grammar ? gets messy. Using \(?) makes it easy for javac to tokenize both strings and templates without feedback from the parser. Note that you would have to add a new escape sequence for $ if you want to use $ in the template.) Other languages can support ${?} at the lexicon level because their strings were designed to support ${?} from the beginning or have simple ways to indicate that the quoted element needs to be treated differently ? different quotes, tag prefix, ? . Back to what I stated at the beginning, I think that \{?} is an advantage for string templates in much the same way that triple quotes works for text blocks, \{?} doesn?t conflict with other languages. Java serves a polyglot universe, where it is not uncommon to embed other language source in a Java app. For example; Object result = JAVASCRIPT.""" let header = "Templates Literals"; let tags = ["template literals", "javascript", "es6"]; let html = `

${header}

    `; for (const x of tags) { html += `
  • ${x}
  • `; } html += `
`; """; or Object result = BASH.""" Recipient=?admin at example.com? Subject=?Greeting? Message=?Welcome to our site? `mail -s ${Subject} ${Recipient} <<< ${Message}` """; Though you would not have the advantage of embedded expressions, it is also possible to use ${?} for your own style of template. We assume existing template libraries will provide similar StringTemplate ?bridging". static final StringTemplate.Processor MY_STYLE = st -> { String text = st.interpolate(); Pattern p = Pattern.compile("\\$\\{(.*?)\\}"); Matcher m = p.matcher(text); List fragments = new ArrayList<>(); List values = new ArrayList<>(); int last = 0; while (m.find()) { fragments.add(text.substring(last, m.start())); values.add(m.group(1)); last = m.end(); } fragments.add(text.substring(last)); return StringTemplate.of(fragments, values); }; public static void main(String[] args) { StringTemplate mailer = MY_STYLE.""" Dear ${name}, This is to inform you that your ${package} will be delivered on ${date}. Respectfully, Big Shop """; Map data = Map.of( "name", "Joan", "package", "bicycle", "date", "May 31" ); System.out.println(StringTemplate.interpolate( mailer.fragments(), mailer.values().stream().map(data::get).toList() )); } ----------------------------------------------------- Dear Joan, This is to inform you that your bicycle will be delivered on May 31. Respectfully, Big Shop ----------------------------------------------------- Hope this frames a better understanding. Cheers, ? Jim -------------- next part -------------- An HTML attachment was scrubbed... URL: From brian.goetz at oracle.com Wed Apr 12 16:21:38 2023 From: brian.goetz at oracle.com (Brian Goetz) Date: Wed, 12 Apr 2023 16:21:38 +0000 Subject: Revisit the String template syntax In-Reply-To: <786405814.34388890.1681237944261.JavaMail.zimbra@univ-eiffel.fr> References: <786405814.34388890.1681237944261.JavaMail.zimbra@univ-eiffel.fr> Message-ID: The backslash syntax is objectively better than the dollar-sign syntax, which is why we selected it in the first place. Reasons included: - Today, ?${name}? is a valid string literal, whereas ?\{name}? is not. - The language already has an escaping mechanism for string contexts; using the one we have is preferable to inventing another one. - Dollar signs will appear in string context fairly regularly, and therefore would need yet more escaping. We knew people would say ?why don?t you ?just? do what ${MyFavoriteLanguage} does?, but this isn?t a reason to reconsider; the fact that other languages have continued to use the dollar-sign convention was well in evidence when the initial design choices were made, and there are no new arguments to support revisiting this question. Whether to use braces or parens or brackets is largely an arbitrary choice, but I don?t see a lot of reason to recall this already-sailing ship. > On Apr 11, 2023, at 2:32 PM, Remi Forax wrote: > > I've promoted this email to amber-spec-experts given that several people on the internet and offline have said more or less the same thing. > > Even if it's not for 21, now that a string template is always prefixed by a template processor, the part in between quote does not need to rely on backslash '\' anymore. > > Should we still keep the current syntax \{...} or should we go to the more usual ${...} syntax ? > > regards, > R?mi > > ----- Original Message ----- >> From: "Octavia Togami" >> To: "amber-spec-comments" >> Sent: Tuesday, April 11, 2023 1:39:20 AM >> Subject: Syntax question for JEP 430: String Templates > >> Hi, >> >> I was reading this portion of the alternatives section: >> >>> For the syntax of embedded expressions we considered using ${...}, but that >>> would require a tag on string templates (either a prefix or a delimiter other >>> than ") to avoid conflicts with legacy code. >> >> And it seems that this is no longer a valid reason, as per [1] there >> is always a required prefix anyways. Is there another reason to avoid >> using this syntax now? >> >> Thanks, >> Octavia >> >> [1]: >> https://mail.openjdk.org/pipermail/amber-spec-experts/2022-October/003631.html From brian.goetz at oracle.com Wed Apr 12 16:22:30 2023 From: brian.goetz at oracle.com (Brian Goetz) Date: Wed, 12 Apr 2023 16:22:30 +0000 Subject: Named record patterns In-Reply-To: <1657524168.34391795.1681238883293.JavaMail.zimbra@univ-eiffel.fr> References: <1657524168.34391795.1681238883293.JavaMail.zimbra@univ-eiffel.fr> Message-ID: <91E532B0-5BE9-43C8-9259-88A4619101E6@oracle.com> I would like to eventually come back for named record patterns, but I think we have to let the dust settle first. On Apr 11, 2023, at 2:48 PM, Remi Forax > wrote: ________________________________ From: "Robbe Pincket" > To: "amber-dev" > Sent: Monday, April 10, 2023 1:27:22 PM Subject: Named record patterns Hi all I was wondering if named record patterns `o instanceof Pair(String left, String right) pair` are still on the table for the future or not. (Not sure if 'named' record pattern is the right name?) Let re-state what is the issue, currently there is no way to create a binding capturing the whole record instance, forcing people to transform the record pattern to a type pattern + when (see below). A previous preview was supporting this case using the syntax case Pair(String left, String right) pair -> ... which did not work well in case someone want the binding to be also have an annotation or be declared final Here is the previous syntax with "final" case final Pair(String left, String right) pair -> ... which is not very readable, the "final" being too far apart from the binding. One solution is to use a keyword like "as" to add a binding at the end of a record pattern (and perhaps other patterns ?) case Pair(String left, String right) as final pair -> ... which as the advantage of grouping the binding and its keyword at the cost of adding a new keyword. R?mi IIRC they were shelfed due to the ambiguity that they could cause in this case, if there also exists a function `when`: ``` switch(o) { case Pair(String left, String right) when when (left == right) -> ... } ``` It feels weird to me however that this feature was shelved just for this case, when a 'simple' rule could be introduced that a record pattern can't introduce a pattern variable with the name of a contextual keyword or at least not `when`. Are there other reasons that record patterns can't introduce a variable that matches the whole pair anymore? It feels like it could be useful, even more so with JEP 443: Unnamed Patterns and Variables (Preview) ``` if (o instanceof ColoredPoint(Point(_, int y), _) cp && y > 0) { doAction(cp); } ``` Instead of ``` if (o instanceof ColoredPoint(Point(int x, int y), Color c) && y > 0) { doAction(new ColoredPoint(new Point(x, y), c)); } ``` or this, if ColoredPoint can both hold `Point` and `Point3D` ``` if (o instanceof ColoredPoint cp && cp.point() instanceof Point(_, int y) && y > 0) { doAction(cp); } ``` or if it can only hold `Point` ``` if (o instanceof ColoredPoint cp && cp.point().y() > 0) { doAction(cp); } ``` Greetings Robbe Pincket -------------- next part -------------- An HTML attachment was scrubbed... URL: From guy.steele at oracle.com Wed Apr 12 16:38:13 2023 From: guy.steele at oracle.com (Guy Steele) Date: Wed, 12 Apr 2023 16:38:13 +0000 Subject: Revisit the String template syntax In-Reply-To: References: <786405814.34388890.1681237944261.JavaMail.zimbra@univ-eiffel.fr> Message-ID: <7B712DA7-6314-467C-8F16-A92CDA47A6A1@oracle.com> > On Apr 12, 2023, at 12:21 PM, Brian Goetz wrote: > > The backslash syntax is objectively better than the dollar-sign syntax, which is why we selected it in the first place. Reasons included: > > - Today, ?${name}? is a valid string literal, whereas ?\{name}? is not. This point is worth expanding on:. It is important to consider not only the effort of writing new code, but also the effort of maintaining and extending old code. With the introduction of string templates, we can expect a fairly common activity to be the modification of an existing string literal to become a string template. Under the current design, this requires doing two things: (1) Add ?STR.? to the front of the string literal. (2) Add ?\{expression}? in various places. Using the dollar-sign syntax would require three steps: (1) Add ?STR.? to the front of the string literal. (2) Add ?\{expression}? in various places. (3) Check the_entire string literal_ for occurrences of ?$? and perhaps replace with "\$?. I don?t think it?s worth it just to make Java look a little bit more like JavaScript (and a little bit less like Java). ?Guy From forax at univ-mlv.fr Sat Apr 15 06:38:10 2023 From: forax at univ-mlv.fr (forax at univ-mlv.fr) Date: Sat, 15 Apr 2023 08:38:10 +0200 (CEST) Subject: Revisit the String template syntax In-Reply-To: <7B712DA7-6314-467C-8F16-A92CDA47A6A1@oracle.com> References: <786405814.34388890.1681237944261.JavaMail.zimbra@univ-eiffel.fr> <7B712DA7-6314-467C-8F16-A92CDA47A6A1@oracle.com> Message-ID: <1407702161.37393088.1681540690809.JavaMail.zimbra@univ-eiffel.fr> ----- Original Message ----- > From: "Guy Steele" > To: "Brian Goetz" > Cc: "Remi Forax" , "amber-spec-experts" > Sent: Wednesday, April 12, 2023 6:38:13 PM > Subject: Re: Revisit the String template syntax >> On Apr 12, 2023, at 12:21 PM, Brian Goetz wrote: >> >> The backslash syntax is objectively better than the dollar-sign syntax, which is >> why we selected it in the first place. Reasons included: >> >> - Today, ?${name}? is a valid string literal, whereas ?\{name}? is not. > > This point is worth expanding on:. It is important to consider not only the > effort of writing new code, but also the effort of maintaining and extending > old code. > > With the introduction of string templates, we can expect a fairly common > activity to be the modification of an existing string literal to become a > string template. > > Under the current design, this requires doing two things: > > (1) Add ?STR.? to the front of the string literal. > (2) Add ?\{expression}? in various places. > > Using the dollar-sign syntax would require three steps: > > (1) Add ?STR.? to the front of the string literal. > (2) Add ?\{expression}? in various places. > (3) Check the_entire string literal_ for occurrences of ?$? and perhaps replace > with "\$?. > > I don?t think it?s worth it just to make Java look a little bit more like > JavaScript (and a little bit less like Java). JavaScript is a user of the ${} syntax but it's a fairly recent addition. In Java, Maven, Gradle through their lineage to Apache Ant, in fact, all projects using the apache common-text StringSubstitutor (or the much older StrSubstitutor) are using the ${} syntax since a very long time. All Java developers are familiar with this syntax for string interpolation. So for a lot of Java developers, the syntax \{} feels alien to Java in comparison. So yes, you have to escape the $ sign, you have to tweak the lexer but, in my opinion, it's a case where familiarity in the whole ecosystem trumps local rationalization. > > ?Guy R?mi From forax at univ-mlv.fr Sat Apr 15 06:50:12 2023 From: forax at univ-mlv.fr (forax at univ-mlv.fr) Date: Sat, 15 Apr 2023 08:50:12 +0200 (CEST) Subject: Revisit the String template syntax In-Reply-To: References: <786405814.34388890.1681237944261.JavaMail.zimbra@univ-eiffel.fr> Message-ID: <1183943058.37394004.1681541412886.JavaMail.zimbra@univ-eiffel.fr> ----- Original Message ----- > From: "Brian Goetz" > To: "Remi Forax" > Cc: "amber-spec-experts" > Sent: Wednesday, April 12, 2023 6:21:38 PM > Subject: Re: Revisit the String template syntax > The backslash syntax is objectively better than the dollar-sign syntax, which is > why we selected it in the first place. Reasons included: > > - Today, ?${name}? is a valid string literal, whereas ?\{name}? is not. > - The language already has an escaping mechanism for string contexts; using the > one we have is preferable to inventing another one. > - Dollar signs will appear in string context fairly regularly, and therefore > would need yet more escaping. > > We knew people would say ?why don?t you ?just? do what ${MyFavoriteLanguage} > does?, but this isn?t a reason to reconsider; the fact that other languages > have continued to use the dollar-sign convention was well in evidence when the > initial design choices were made, and there are no new arguments to support > revisiting this question. > > Whether to use braces or parens or brackets is largely an arbitrary choice, but > I don?t see a lot of reason to recall this already-sailing ship. I believe that the backslash syntax is better if we were in 1995, trying to design Java but since then, the dollar-sign syntax have been the go to syntax for string interpolation in the Java ecosystem. That's why actual most of the Java developers prefer the dollar-sign syntax to the backslash syntax (at least the one at Devoxx France i've asked), because they to not have to reconfigure their brain to recognize a new syntax. R?mi > > > >> On Apr 11, 2023, at 2:32 PM, Remi Forax wrote: >> >> I've promoted this email to amber-spec-experts given that several people on the >> internet and offline have said more or less the same thing. >> >> Even if it's not for 21, now that a string template is always prefixed by a >> template processor, the part in between quote does not need to rely on >> backslash '\' anymore. >> >> Should we still keep the current syntax \{...} or should we go to the more usual >> ${...} syntax ? >> >> regards, >> R?mi >> >> ----- Original Message ----- >>> From: "Octavia Togami" >>> To: "amber-spec-comments" >>> Sent: Tuesday, April 11, 2023 1:39:20 AM >>> Subject: Syntax question for JEP 430: String Templates >> >>> Hi, >>> >>> I was reading this portion of the alternatives section: >>> >>>> For the syntax of embedded expressions we considered using ${...}, but that >>>> would require a tag on string templates (either a prefix or a delimiter other >>>> than ") to avoid conflicts with legacy code. >>> >>> And it seems that this is no longer a valid reason, as per [1] there >>> is always a required prefix anyways. Is there another reason to avoid >>> using this syntax now? >>> >>> Thanks, >>> Octavia >>> >>> [1]: > >> https://mail.openjdk.org/pipermail/amber-spec-experts/2022-October/003631.html From amaembo at gmail.com Sat Apr 15 07:48:14 2023 From: amaembo at gmail.com (Tagir Valeev) Date: Sat, 15 Apr 2023 09:48:14 +0200 Subject: Revisit the String template syntax In-Reply-To: <1407702161.37393088.1681540690809.JavaMail.zimbra@univ-eiffel.fr> References: <786405814.34388890.1681237944261.JavaMail.zimbra@univ-eiffel.fr> <7B712DA7-6314-467C-8F16-A92CDA47A6A1@oracle.com> <1407702161.37393088.1681540690809.JavaMail.zimbra@univ-eiffel.fr> Message-ID: Hello, R?mi! > JavaScript is a user of the ${} syntax but it's a fairly recent addition. > > In Java, Maven, Gradle through their lineage to Apache Ant, in fact, all projects using the apache common-text StringSubstitutor (or the much older StrSubstitutor) are using the ${} syntax since a very long time. All Java developers are familiar with this syntax for string interpolation. > > So for a lot of Java developers, the syntax \{} feels alien to Java in comparison. So yes, you have to escape the $ sign, you have to tweak the lexer but, in my opinion, it's a case where familiarity in the whole ecosystem trumps local rationalization. To me, this is actually an argument against ${}. With \{}, the users will have a clear difference between language-supported interpolation and external library interpolation. I can imagine that in some cases, you may need to use both. For example, imagine that you are generating build.xml or pom.xml and want to store strings containing ${...} as is without interpolating right now, because they refer to the properties defined in that file. However, you want to interpolate eagerly some other parts of these strings using Java string interpolation. Something like STR."${project.basedir}/build/\{generateTempDirName()}/". You can easily combine two approaches with \{} escapes. It would be much harder and much more error prone to create such templates if the same syntax was used for both Java and external interpolation. I think that distinguished interpolation syntax, which is rarely used in other contexts, is actually an advantage. People will get used to it. With best regards, Tagir Valeev From forax at univ-mlv.fr Sat Apr 15 08:28:15 2023 From: forax at univ-mlv.fr (forax at univ-mlv.fr) Date: Sat, 15 Apr 2023 10:28:15 +0200 (CEST) Subject: Revisit the String template syntax In-Reply-To: References: <786405814.34388890.1681237944261.JavaMail.zimbra@univ-eiffel.fr> <7B712DA7-6314-467C-8F16-A92CDA47A6A1@oracle.com> <1407702161.37393088.1681540690809.JavaMail.zimbra@univ-eiffel.fr> Message-ID: <1692755242.37405377.1681547295975.JavaMail.zimbra@univ-eiffel.fr> ----- Original Message ----- > From: "Tagir Valeev" > To: "Remi Forax" > Cc: "Guy Steele" , "Brian Goetz" , "amber-spec-experts" > > Sent: Saturday, April 15, 2023 9:48:14 AM > Subject: Re: Revisit the String template syntax > Hello, R?mi! > >> JavaScript is a user of the ${} syntax but it's a fairly recent addition. >> >> In Java, Maven, Gradle through their lineage to Apache Ant, in fact, all >> projects using the apache common-text StringSubstitutor (or the much older >> StrSubstitutor) are using the ${} syntax since a very long time. All Java >> developers are familiar with this syntax for string interpolation. >> >> So for a lot of Java developers, the syntax \{} feels alien to Java in >> comparison. So yes, you have to escape the $ sign, you have to tweak the lexer >> but, in my opinion, it's a case where familiarity in the whole ecosystem trumps >> local rationalization. > > To me, this is actually an argument against ${}. With \{}, the users > will have a clear difference between language-supported interpolation > and external library interpolation. I can imagine that in some cases, > you may need to use both. For example, imagine that you are generating > build.xml or pom.xml and want to store strings containing ${...} as is > without interpolating right now, because they refer to the properties > defined in that file. However, you want to interpolate eagerly some > other parts of these strings using Java string interpolation. > Something like STR."${project.basedir}/build/\{generateTempDirName()}/". > You can easily combine two approaches with \{} escapes. It would be > much harder and much more error prone to create such templates if the > same syntax was used for both Java and external interpolation. It's not really harder, you escape the first dollar-sign, STR."\${project.basedir}/build/${generateTempDirName()}/" > I think that distinguished interpolation syntax, which is rarely used in other > contexts, is actually an advantage. People will get used to it. The real question is more, do we want two syntax for conceptually the same thing or not ? Here is an example with an annotation, @Bean class SpringBean { @Value("${myproperty}") private String myproperty; public void foo() { System.out.println(STR."myproperty: ${myproperty}"); } } > > With best regards, > Tagir Valeev regards, R?mi From brian.goetz at oracle.com Sat Apr 15 13:07:30 2023 From: brian.goetz at oracle.com (Brian Goetz) Date: Sat, 15 Apr 2023 13:07:30 +0000 Subject: Revisit the String template syntax In-Reply-To: <1183943058.37394004.1681541412886.JavaMail.zimbra@univ-eiffel.fr> References: <786405814.34388890.1681237944261.JavaMail.zimbra@univ-eiffel.fr> <1183943058.37394004.1681541412886.JavaMail.zimbra@univ-eiffel.fr> Message-ID: <2558AC1A-1097-4390-AAA9-9F4081E27733@oracle.com> Libraries don?t have the option to use \ because they can?t modify the language grammar. This is why they gravitate towards inline syntax like $ ? because they have no choice. They?ve done what they have to. The language has different options. I understand why you think familiarity might justify doing the objectively worse thing, but am confident we would regret it if we gave into this temptation. This is a pretty clear no. Sent from my iPad > On Apr 15, 2023, at 2:50 AM, forax at univ-mlv.fr wrote: > > ?----- Original Message ----- >> From: "Brian Goetz" >> To: "Remi Forax" >> Cc: "amber-spec-experts" >> Sent: Wednesday, April 12, 2023 6:21:38 PM >> Subject: Re: Revisit the String template syntax > >> The backslash syntax is objectively better than the dollar-sign syntax, which is >> why we selected it in the first place. Reasons included: >> >> - Today, ?${name}? is a valid string literal, whereas ?\{name}? is not. >> - The language already has an escaping mechanism for string contexts; using the >> one we have is preferable to inventing another one. >> - Dollar signs will appear in string context fairly regularly, and therefore >> would need yet more escaping. >> >> We knew people would say ?why don?t you ?just? do what ${MyFavoriteLanguage} >> does?, but this isn?t a reason to reconsider; the fact that other languages >> have continued to use the dollar-sign convention was well in evidence when the >> initial design choices were made, and there are no new arguments to support >> revisiting this question. >> >> Whether to use braces or parens or brackets is largely an arbitrary choice, but >> I don?t see a lot of reason to recall this already-sailing ship. > > > I believe that the backslash syntax is better if we were in 1995, trying to design Java but since then, the dollar-sign syntax have been the go to syntax for string interpolation in the Java ecosystem. That's why actual most of the Java developers prefer the dollar-sign syntax to the backslash syntax (at least the one at Devoxx France i've asked), because they to not have to reconfigure their brain to recognize a new syntax. > > R?mi > >> >> >> >>>> On Apr 11, 2023, at 2:32 PM, Remi Forax wrote: >>> >>> I've promoted this email to amber-spec-experts given that several people on the >>> internet and offline have said more or less the same thing. >>> >>> Even if it's not for 21, now that a string template is always prefixed by a >>> template processor, the part in between quote does not need to rely on >>> backslash '\' anymore. >>> >>> Should we still keep the current syntax \{...} or should we go to the more usual >>> ${...} syntax ? >>> >>> regards, >>> R?mi >>> >>> ----- Original Message ----- >>>> From: "Octavia Togami" >>>> To: "amber-spec-comments" >>>> Sent: Tuesday, April 11, 2023 1:39:20 AM >>>> Subject: Syntax question for JEP 430: String Templates >>> >>>> Hi, >>>> >>>> I was reading this portion of the alternatives section: >>>> >>>>> For the syntax of embedded expressions we considered using ${...}, but that >>>>> would require a tag on string templates (either a prefix or a delimiter other >>>>> than ") to avoid conflicts with legacy code. >>>> >>>> And it seems that this is no longer a valid reason, as per [1] there >>>> is always a required prefix anyways. Is there another reason to avoid >>>> using this syntax now? >>>> >>>> Thanks, >>>> Octavia >>>> >>>> [1]: >>>> https://mail.openjdk.org/pipermail/amber-spec-experts/2022-October/003631.html From brian.goetz at oracle.com Mon Apr 17 14:05:18 2023 From: brian.goetz at oracle.com (Brian Goetz) Date: Mon, 17 Apr 2023 10:05:18 -0400 Subject: Fwd: String templates and constant expressions In-Reply-To: References: Message-ID: This was received on the -comments list.? It raises a question which I realize now was not explicitly discussed with the EG, but which was considered in internal discussions: can the result of a string template ever be considered a constant expression? At first, one might thing that a string template whose embedded expressions (and processor) are constant expressions could be a constant expression.? The questioner's motivation is that the arguments of annotations must be constant expressions, so this would enrich the set of things we can put in annotations. Unfortunately, the bar for "constant expression" in the JLS is quite high (and even that doesn't necessarily get us to annotation parameters.)? For String constants, the compiler would "just" have to fold the string at compile time -- but it would need need permission from the spec to do so, which means we have to specify at least part of the "constant folding" story for a very narrow and ad-hoc benefit, and which would likely lead to an RFE tail of "can you please allow XYZ to be a constant expression".? And for types more interesting than String/int/friends, we'd have to do more -- we'd have to update the specification of annotations to support types other than the set of types that currently have an encoding in JVMS 4.7.16.? (We explored this for an arguably more valuable use case -- method references as annotation parameters -- and while there was nothing wrong with that in principle, there was significant work in the classfile spec, VM, compiler, and reflection (and ASM and friends) to plumb it end to end, and this didn't make the priority cut.) So the short answer to the question is "no", and the slightly longer answer is "you want constant folding, but we're not going to do constant folding in little ad-hoc bits." -------- Forwarded Message -------- Subject: String templates and constant expressions Date: Sat, 15 Apr 2023 19:46:07 +0200 From: Jens Lidestr?m To: amber-spec-comments at openjdk.java.net Dear experts and observers, A recent message in the thread "Revisit the String template syntax" compared the Spring property annotation syntax with the proposed String template syntax. @Value("${myproperty}") private String myproperty; I have the somewhat vague question: Are there any relation between the use case of these property annotations and the use case of string templates? The argument of the @Value annotation must be a String constant expression. Can a string template be used as a constant expression? Maybe if all its arguments are themselves are constants? Could a property syntax such as Spring's use string templates? Could code like the following do anything sensible?: @Value("\{someTemplateArg}") private String someField; Maybe like this: @Value("\{MyProperties.SOME_PROPERTY_KEY}") private String someField; Maybe there is no relation and the answer is simply "no". But maybe it worth to think about. I don't see constant expressions mentioned in the JEP: https://openjdk.org/jeps/430 Regards, Jens Lidestr?m PS: This feature in general seems very good to me. -------------- next part -------------- An HTML attachment was scrubbed... URL: From forax at univ-mlv.fr Mon Apr 17 15:16:25 2023 From: forax at univ-mlv.fr (Remi Forax) Date: Mon, 17 Apr 2023 17:16:25 +0200 (CEST) Subject: String templates and constant expressions In-Reply-To: References: Message-ID: <2039965590.38108304.1681744585219.JavaMail.zimbra@univ-eiffel.fr> > From: "Brian Goetz" > To: "amber-spec-experts" > Sent: Monday, April 17, 2023 4:05:18 PM > Subject: Fwd: String templates and constant expressions > This was received on the -comments list. It raises a question which I realize > now was not explicitly discussed with the EG, but which was considered in > internal discussions: can the result of a string template ever be considered a > constant expression? > At first, one might thing that a string template whose embedded expressions (and > processor) are constant expressions could be a constant expression. The > questioner's motivation is that the arguments of annotations must be constant > expressions, so this would enrich the set of things we can put in annotations. > Unfortunately, the bar for "constant expression" in the JLS is quite high (and > even that doesn't necessarily get us to annotation parameters.) For String > constants, the compiler would "just" have to fold the string at compile time -- > but it would need need permission from the spec to do so, which means we have > to specify at least part of the "constant folding" story for a very narrow and > ad-hoc benefit, and which would likely lead to an RFE tail of "can you please > allow XYZ to be a constant expression". And for types more interesting than > String/int/friends, we'd have to do more -- we'd have to update the > specification of annotations to support types other than the set of types that > currently have an encoding in JVMS 4.7.16. (We explored this for an arguably > more valuable use case -- method references as annotation parameters -- and > while there was nothing wrong with that in principle, there was significant > work in the classfile spec, VM, compiler, and reflection (and ASM and friends) > to plumb it end to end, and this didn't make the priority cut.) > So the short answer to the question is "no", and the slightly longer answer is > "you want constant folding, but we're not going to do constant folding in > little ad-hoc bits." Note that we discussed about introducing method references in annotation for Java 8. This is now a little simpler because, since 11, we have constant dynamic and we can extend the annotation tag "c" to work with any constants provided by a constant dynamic instead of only "constant classes" (the same way the meaning of the opcode ldc was extended to support constant dynamic). At least for ASM and the reflection, this change does not change the API, only the implementation. This is still a big change, javac and the VM needs to be updated but this is less scary than before constant dynamic was introduced. R?mi > -------- Forwarded Message -------- > Subject: String templates and constant expressions > Date: Sat, 15 Apr 2023 19:46:07 +0200 > From: Jens Lidestr?m [ mailto:jens at lidestrom.se | ] > To: [ mailto:amber-spec-comments at openjdk.java.net | > amber-spec-comments at openjdk.java.net ] > Dear experts and observers, > A recent message in the thread "Revisit the String template syntax" compared the > Spring property annotation syntax with the proposed String template syntax. > @Value("${myproperty}") > private String myproperty; > I have the somewhat vague question: Are there any relation between the use case > of these property annotations and the use case of string templates? > The argument of the @Value annotation must be a String constant expression. > Can a string template be used as a constant expression? Maybe if all its > arguments are themselves are constants? Could a property syntax such as > Spring's use string templates? > Could code like the following do anything sensible?: > @Value("\{someTemplateArg}") > private String someField; > Maybe like this: > @Value("\{MyProperties.SOME_PROPERTY_KEY}") > private String someField; > Maybe there is no relation and the answer is simply "no". But maybe it worth to > think about. > I don't see constant expressions mentioned in the JEP: [ > https://openjdk.org/jeps/430 | https://openjdk.org/jeps/430 ] > Regards, > Jens Lidestr?m > PS: This feature in general seems very good to me. -------------- next part -------------- An HTML attachment was scrubbed... URL: From forax at univ-mlv.fr Mon Apr 17 15:24:25 2023 From: forax at univ-mlv.fr (Remi Forax) Date: Mon, 17 Apr 2023 17:24:25 +0200 (CEST) Subject: String templates and constant expressions In-Reply-To: <2039965590.38108304.1681744585219.JavaMail.zimbra@univ-eiffel.fr> References: <2039965590.38108304.1681744585219.JavaMail.zimbra@univ-eiffel.fr> Message-ID: <630085108.38114270.1681745065869.JavaMail.zimbra@univ-eiffel.fr> > From: "Remi Forax" > To: "Brian Goetz" > Cc: "amber-spec-experts" > Sent: Monday, April 17, 2023 5:16:25 PM > Subject: Re: String templates and constant expressions >> From: "Brian Goetz" >> To: "amber-spec-experts" >> Sent: Monday, April 17, 2023 4:05:18 PM >> Subject: Fwd: String templates and constant expressions >> This was received on the -comments list. It raises a question which I realize >> now was not explicitly discussed with the EG, but which was considered in >> internal discussions: can the result of a string template ever be considered a >> constant expression? >> At first, one might thing that a string template whose embedded expressions (and >> processor) are constant expressions could be a constant expression. The >> questioner's motivation is that the arguments of annotations must be constant >> expressions, so this would enrich the set of things we can put in annotations. >> Unfortunately, the bar for "constant expression" in the JLS is quite high (and >> even that doesn't necessarily get us to annotation parameters.) For String >> constants, the compiler would "just" have to fold the string at compile time -- >> but it would need need permission from the spec to do so, which means we have >> to specify at least part of the "constant folding" story for a very narrow and >> ad-hoc benefit, and which would likely lead to an RFE tail of "can you please >> allow XYZ to be a constant expression". And for types more interesting than >> String/int/friends, we'd have to do more -- we'd have to update the >> specification of annotations to support types other than the set of types that >> currently have an encoding in JVMS 4.7.16. (We explored this for an arguably >> more valuable use case -- method references as annotation parameters -- and >> while there was nothing wrong with that in principle, there was significant >> work in the classfile spec, VM, compiler, and reflection (and ASM and friends) >> to plumb it end to end, and this didn't make the priority cut.) >> So the short answer to the question is "no", and the slightly longer answer is >> "you want constant folding, but we're not going to do constant folding in >> little ad-hoc bits." > Note that we discussed about introducing method references in annotation for > Java 8. > This is now a little simpler because, since 11, we have constant dynamic and we > can extend the annotation tag "c" to work with any constants provided by a > constant dynamic instead of only "constant classes" (the same way the meaning > of the opcode ldc was extended to support constant dynamic). > At least for ASM and the reflection, this change does not change the API, only > the implementation. > This is still a big change, javac and the VM needs to be updated but this is > less scary than before constant dynamic was introduced. > R?mi Just to be clear, i'm not asking to make string template constant expression, but just saying that introducing new constant expressions inside annotations is less an issue than it was because we have better tools. R?mi >> -------- Forwarded Message -------- >> Subject: String templates and constant expressions >> Date: Sat, 15 Apr 2023 19:46:07 +0200 >> From: Jens Lidestr?m [ mailto:jens at lidestrom.se | ] >> To: [ mailto:amber-spec-comments at openjdk.java.net | >> amber-spec-comments at openjdk.java.net ] >> Dear experts and observers, >> A recent message in the thread "Revisit the String template syntax" compared the >> Spring property annotation syntax with the proposed String template syntax. >> @Value("${myproperty}") >> private String myproperty; >> I have the somewhat vague question: Are there any relation between the use case >> of these property annotations and the use case of string templates? >> The argument of the @Value annotation must be a String constant expression. >> Can a string template be used as a constant expression? Maybe if all its >> arguments are themselves are constants? Could a property syntax such as >> Spring's use string templates? >> Could code like the following do anything sensible?: >> @Value("\{someTemplateArg}") >> private String someField; >> Maybe like this: >> @Value("\{MyProperties.SOME_PROPERTY_KEY}") >> private String someField; >> Maybe there is no relation and the answer is simply "no". But maybe it worth to >> think about. >> I don't see constant expressions mentioned in the JEP: [ >> https://openjdk.org/jeps/430 | https://openjdk.org/jeps/430 ] >> Regards, >> Jens Lidestr?m >> PS: This feature in general seems very good to me. -------------- next part -------------- An HTML attachment was scrubbed... URL: From brian.goetz at oracle.com Mon Apr 17 15:26:43 2023 From: brian.goetz at oracle.com (Brian Goetz) Date: Mon, 17 Apr 2023 11:26:43 -0400 Subject: String templates and constant expressions In-Reply-To: <2039965590.38108304.1681744585219.JavaMail.zimbra@univ-eiffel.fr> References: <2039965590.38108304.1681744585219.JavaMail.zimbra@univ-eiffel.fr> Message-ID: > Note that we discussed about introducing method references in > annotation for Java 8. > This is now a little simpler because, since 11, we have constant > dynamic and we can extend the annotation tag "c" to work with any > constants provided by a constant dynamic instead of only "constant > classes" (the same way the meaning of the opcode ldc was extended to > support constant dynamic). This is definitely a convenience for implementation, though there are also other considerations that might influence the design of the attribute in other directions.? In general, we are likely to remain extremely conservative about putting "more stuff in annotations". > > At least for ASM and the reflection, this change does not change the > API, only the implementation. True for ASM because it uses Object and then uses instanceof chains to make sure you've provided a good kind of Object, but not necessarily true for all bytecode APIs, which might use sealed types. > This is still a big change, javac and the VM needs to be updated but > this is less scary than before constant dynamic was introduced. Yes, not only an invasive implementation change, but there are also some nontrivial design questions as well.? (Annotations prove once again to be "the gift that keeps on giving".) -------------- next part -------------- An HTML attachment was scrubbed... URL: From gavin.bierman at oracle.com Thu Apr 20 21:19:14 2023 From: gavin.bierman at oracle.com (Gavin Bierman) Date: Thu, 20 Apr 2023 21:19:14 +0000 Subject: Draft Spec for Statements before Super() (JEP 447) Message-ID: Dear experts: The first draft of the spec change document for the feature Statements before super() [1] is now available at: https://cr.openjdk.org/~gbierman/jep447/latest/ Please give us your feedback (either on this list or directly to me). Thanks, Gavin [1] Statements before super(): https://openjdk.org/jeps/447 -------------- next part -------------- An HTML attachment was scrubbed... URL: From gavin.bierman at oracle.com Thu Apr 20 21:26:17 2023 From: gavin.bierman at oracle.com (Gavin Bierman) Date: Thu, 20 Apr 2023 21:26:17 +0000 Subject: [Resend] Draft Spec for Statements before Super() (JEP 447) Message-ID: <7405ACA9-C88D-4170-A758-714B6F9CBD27@oracle.com> [Resending as the hyperlinks got mangled] Dear experts: The first draft of the spec change document for the feature Statements before super() [1] is now available at: https://cr.openjdk.org/~gbierman/jep447/latest/ Please give us your feedback (either on this list or directly to me). Thanks, Gavin [1] Statements before super(): https://openjdk.org/jeps/447 From gavin.bierman at oracle.com Thu Apr 20 21:29:03 2023 From: gavin.bierman at oracle.com (Gavin Bierman) Date: Thu, 20 Apr 2023 21:29:03 +0000 Subject: [Resend] Draft Spec for Statements before Super() (JEP 447) In-Reply-To: <7405ACA9-C88D-4170-A758-714B6F9CBD27@oracle.com> References: <7405ACA9-C88D-4170-A758-714B6F9CBD27@oracle.com> Message-ID: <0A605E48-05AA-4EE2-8861-5E50225A7336@oracle.com> Third time lucky: Dear experts: The first draft of the spec change document for the feature Statements before super() [1] is now available at: https://cr.openjdk.org/~gbierman/jep447/latest/ Please give us your feedback (either on this list or directly to me). Thanks, Gavin [1] Statements before super(): https://openjdk.org/jeps/447 On 20 Apr 2023, at 22:26, Gavin Bierman wrote: [Resending as the hyperlinks got mangled] Dear experts: The first draft of the spec change document for the feature Statements before super() [1] is now available at: https://cr.openjdk.org/~gbierman/jep447/latest/ Please give us your feedback (either on this list or directly to me). Thanks, Gavin [1] Statements before super(): https://openjdk.org/jeps/447 -------------- next part -------------- An HTML attachment was scrubbed... URL: From alex.buckley at oracle.com Thu Apr 20 22:42:21 2023 From: alex.buckley at oracle.com (Alex Buckley) Date: Thu, 20 Apr 2023 15:42:21 -0700 Subject: Draft Spec for Statements before Super() (JEP 447) In-Reply-To: References: Message-ID: <55ea813b-56a5-be2a-41c9-ac921651e628@oracle.com> Hi Gavin, a few comments on a super draft for a super() feature. On 4/20/2023 2:19 PM, Gavin Bierman wrote: > The first draft of the spec change document for the feature Statements > before super() [1] is now available at: > > https://cr.openjdk.org/~gbierman/jep447/latest/ 1. The decision to sever constructor bodies from "static context" is righteous. As the edit in 8.1.3 implies, a static context is properly defined to involve _no_ current instance, versus the traditional definition of there's-a-current-instance-but-you-can't-refer-to-it. It is right to introduce a new kind of context for (some of) a constructor body, where uniquely there's-a-current-instance-but-you-can't-refer-to-it. 2. For the new kind of context, I recommend "pre-construction context" instead of "pre-initialization context". Initialization is what happens to a class prior to any constructors being run. The last paragraph of 15.9 is keen on a class being "instantiated" but I think most people would trip over "pre-instantiation context" and would thank you for the plainspoken "pre-construction context". 3. The new kind of context is introduced as a _dynamic_ artifact -- "... a pre-initialization context *of the current object*" -- but it's sweeping out a lexical space. Even the dynamic story about new instances in 12.5 doesn't mention the pre-initialization context *of the new instance*. Wouldn't the following pattern work throughout: "It is a compile-time error if a this expression occurs in a static context (8.1.3) or in ~a~ +the+ pre-initialization context of ~the associated instance~ +a constructor body+ (8.8.7.1)." 4. In 8.8.7.1, you mention "An explicit constructor invocation *statement* ...". It would be worth noting in 8.8.7 that an explicit constructor invocation is not a statement by the technical meaning of 14.5, yet shares most of the characteristics of statements such as (i) having normal and abrupt completion, and (ii) potentially being unreachable by 14.22. (You ban `return` in the prologue, but see below for a notional ctor body that I'm certain javac would sensibly reject for an unreachable `super();` "statement".) ``` P: { System.out.println("ctor started"); break P; super(); } System.out.println("ctor finished"); ``` Alex From archie.cobbs at gmail.com Fri Apr 21 20:55:06 2023 From: archie.cobbs at gmail.com (Archie Cobbs) Date: Fri, 21 Apr 2023 15:55:06 -0500 Subject: Draft Spec for Statements before Super() (JEP 447) In-Reply-To: <55ea813b-56a5-be2a-41c9-ac921651e628@oracle.com> References: <55ea813b-56a5-be2a-41c9-ac921651e628@oracle.com> Message-ID: Hi Alex, Great comments - thanks. I like "pre-construction context" better also. On Thu, Apr 20, 2023 at 5:42?PM Alex Buckley wrote: > You ban `return` in the prologue, but see below > for a notional ctor body that I'm certain javac would sensibly reject > for an unreachable `super();` "statement".) > > ``` > P: { > System.out.println("ctor started"); > break P; > super(); > } > System.out.println("ctor finished"); > ``` > Maybe we need a parenthetical comment that points out how any nesting of a super()/this() call inside a block or anything else is disallowed by the language production for *ConstructorBody*, in 8.8.7, which effectively requires *ExplicitConstructorInvocation* to be top level. -Archie -- Archie L. Cobbs -------------- next part -------------- An HTML attachment was scrubbed... URL: From brian.goetz at oracle.com Thu Apr 27 16:03:17 2023 From: brian.goetz at oracle.com (Brian Goetz) Date: Thu, 27 Apr 2023 12:03:17 -0400 Subject: Fwd: B3, default values, and implicit initialization In-Reply-To: References: Message-ID: <14ec8e81-ecd6-27eb-cacb-dabb2791224a@oracle.com> The following was received on amber-spec-comments. Without deep-diving into the specific syntax suggestion, which I'll summarize as "default values are values, and we have fields to specify values, so why wouldn't we do that?", the main thing here is that there is a concern that we might make the distinction between B2 and B3 "too subtle", and that would "lead to overuse of B3". There is a challenge with the specifics here, in that the stated goal is to explicitly specify the default, but (a) it is not possible to explicitly specify an arbitrary default (which using a field would imply), and (b) it is not possible to conveniently denote "the instance where all the fields have their default values".? So I don't think the field-centric approach is a winner, but again, that's not the main value of such a suggestion. I'm not a fan of arguments that start with "we should force the user..."; while we often do go down this road (e.g., subtypes of sealed types must be explicitly sealed, final, or non-sealed, to avoid ambiguities over defaults), such arguments should start with "here is what would go wrong if people didn't understand the defaults properly." So, what I'd like to see is more specifics on _how_ B3 might be overused and _why_ that is bad before considering these syntactic directions. Some additional relevant observations about the current direction: ?- Value classes, without any reference to the special property of "usable without initialization" or atomicity under race, are very simple: they are like ordinary classes without identity.? As a direct consequence, identity-sensitive operations (==, synchronized, etc) are either redefined based on state or are partialized, and features that require identity (mutability, layout polymorphism) are disallowed.? They are otherwise like identity classes in every other way -- they are reference types, variables of such class types are nullable, etc. This is the "simplest possible" interpretation of value classes, in that the only thing we take away is identity. ?- This interpretation of value classes is a "safe default"; if you don't go the extra mile and talk about uninitialized use, or atomicity, you get something with the same safety properties as identity classes.? You have to explicitly do something extra to get the B3 properties. -------- Forwarded Message -------- Subject: Re: B3, default values, and implicit initialization Date: Thu, 27 Apr 2023 11:23:54 +0100 From: Stephen Colebourne To: valhalla-spec-comments at openjdk.java.net From my perspective, the difference between B2 and B3 is vital, as I fear developers will greatly overuse B3. I don't think "default constructors" are the right focus. The initial discussions of B2 vs B3 focussed on one main question - does the type have a sensible default. `LocalDate` does not, but `Decimal` or `Optional` does (zero or empty). The big issue Valhalla faces during adoption from my perspective is the messaging, which is far too easy to simplify to B3 faster than B2 faster than B1. The net result would be many more 1979-01-01 type bugs. Without great care here we could be creating the potential for many null-like "million-dollar mistakes". To counteract this, the syntax IMO needs to place the issue at hand directly in the face of the developer. And the key question is "what is the sensible default value for an instance of this type". Given this, I think all authors of *all* value types should be forced to *explicitly* define what the default value is. ie. it isn't something where the language should choose one or the other as the default (sic). The obvious syntax is a field, which is implicitly public static final. I don't feel that a class-level keyword is the right choice here: public value LocalDate { default = null; } public value Decimal { default = new; } In each case, the author has had to explicitly choose what the sensible default is, and therefore implicitly chooses whether it is B2 and B3 - without any opportunity to be distracted by the performance model. Neither B2 or B3 is chosen as the favourite by the language. "It is a compilation error when a value class declaration does not specify a default value". By contrast, default constructors are one or two steps removed from the actual decision point that the class author should actually be thinking about, which is what the sensible default is. It is also the case that the default constructor is never actually invoked, which will be an ongoing point of surprise. Terminology in specs just talks about what the default value is, eg "authors should select the most appropriate default value for their domain", "arrays are initialised to the default value of a value type" or "if the default is null then ...": The syntax is intended to make it perfectly reasonable to ask for `LocalDate.default` or `Decimal.default` and get a sensible answer - it looks like a "normal" constant in code. The use of `default = new` by itself deliberately invokes the idea of a default constructor that does nothing, without the need to spell it out. Javadoc can be added to the `default` constant, which is very helpful. For example it might include justification as to why LocaleDate does not have a default value of 0000-01-01 or 1970-01-01. Stephen On Tue, 28 Mar 2023 at 20:13, Brian Goetz wrote: > The recent update of JEP 401 contained a number of refinements to the user model, specifically, separating the primitive/reference distinction into a number of smaller distinctions (e.g., nullable vs non-nullable, optional vs required construction.) Overall this has been a very positive step forward. > > We still have a need for the distinction between what we've been calling B2 and B3; JEP 401 currently frames that in terms of "construction is optional." This is a big step forward; indeed, the key difference between them is whether the class _needs_ the "variables start out as null, and all instances are created by constructors" protection, or whether it admits the lighter-weight initialization protocol of "there's a a standard zero value, null-free variables are initialized to that" that primitives enjoy today. (Note that B3 classes don't require this lighter protocol, they merely enable it, much as primitives all give you the option of boxing to get the full conservative initialization protocol.) > > The idea of framing this as "construction is optional" is a good one, but the expression of it proposed in JEP 401 feels "not quite there". In this note I'll propose an alternative presentation, but the main goal here is around terminology and user model rather than syntax (so please keep the syntax agitation to a reasonable level.) > > The key distinction between B2 and B3 is that B3 has a _default value_ which the VM can summon at will. This enables non-nullable heap variables to be flattened, because we can initialize these the same way we initialize other fields and array elements. Further, that default value is highly constrained; it is a physical zero, the result of initializing all fields to their default value. > > Flattening is of course a goal, but it is not something that exists in the programming model -- its just an optimization. What exists in the programming model is the default value, and what this unlocks is the possibility for variables to be _implicitly initializated_. Reference-typed variables today are _explicitly initialized_; variables start out null and have to be initialized with a constructed value. A class with a default value has the option (opted in through null-exclusion) for its variables to be implicitly initialized, which, like primitives, means that they start out with a valid default value, and can be further assigned to. > > Framed this way, the Valhalla performance story simplifies to: > > - Give up identity, get flattening on the stack; > - Further give up explicit initialization, get flattening for small objects on the heap; > - Further give up atomicity, get flattening for larger objects on the heap. > > Giving up explicit initialization entails both the class opting out of explicit initialization, _and_ the variable opting out of nullity. > > The key new terminology that comes out of this is implicit vs explicit initialization. > > > Syntactically, my preference is to indicate that the default value can be summoned by giving a value class a _default constructor_: > > value class Complex { > public final double re, im; > > public default Complex(); > } > > A default constructor has no arguments, no body, no throws clause, and implicitly initializes all fields to their default values. Unlike identity classes, value classes don't get constructions implicitly; a value class must declare at least one constructor, default or otherwise. This replaces the idea of "optional constructor", which is a negative statement about construction ("but you don't have to call me"), with a more direct and positive statement that there is a _default constructor_ with the required properties. > > Note that this is similar to the existing concept of "default constructor", which you get for free in an identity class if you don't specify any constructors. It is possible we can unify these features (and also with constructors in "agnostic" abstract classes), but first let's work out what it would mean in value classes, and see if we like it. > > In this model, a B3 class is just a value class with a default constructor -> a default constructor means that you have the choice of implicit or explicit initialization -> non-nullity at the use site opts into implicit initialization -> B3! gets flattening (for small layouts.) > > -------------- next part -------------- An HTML attachment was scrubbed... URL: