Are they trying to make Scala look more complicated than the other languages on purpose? The Scala example f"$x%d plus $y%d equals ${x + y}%d" could be written simply as s"$x plus $y equals ${x + y}"
Yes, Java is legit scared of Scala's rising popularity.
JEP 430: String Templates (Preview) Proposed to Target Java 21
61–70 of 246 posts
Re: JEP 430: String Templates (Preview) Proposed to Target Java 21
#62 StringProcessor INTER = (StringTemplate st) -> {
String placeHolder = "•";
String stencil = String.join(placeHolder, fragments);
for (Object value : st.values()) {
String v = String.valueOf(value);
stencil = stencil.replaceFirst(placeHolder, v);
}
return stencil;
};
‘fragments’ should be ‘st.fragments()’ here I believe to make it compile.Re: JEP 430: String Templates (Preview) Proposed to Target Java 21
#63Earlier quoted context omitted.
We could have unsigned integers but we're choosing not to because on the whole their disadvantages outweigh their advantages. On the other hand, once we have user-defined value types, you'll be able to define unsigned integers in a library if you want. The extensibility and power of string templates were a requirement; security experts quite simply vetoed adding string interpolation as it's just too dangerous, especi…
Python is also widely used server-side, and they introduced f-strings with simple and friendly syntax a few years ago. JS added template literals in 2015’s ES6, when Node.js was very much a thing. Why is Java special here?
Re: JEP 430: String Templates (Preview) Proposed to Target Java 21
#64It's interesting how C# is always far ahead of Java, they introduced it way earlier, the syntax is simpler, and you can make is safe by using FormattableString as the param type, for example in EF you can do this without worrying about SQL injection: FromSql($"EXECUTE dbo.GetMostPopularBlogsForUser {user}") https://learn.microsoft.com/en-us/ef/core/querying/sql-queri...
…and they also always default to formatting with CurrentCulture instead of InvarintCulture. Apparently this was by-design as interpolated strings were never originally intended for generating machine-readable strings.
Finally, there’s no way to perform common “mini-templating” with a FormattableString, such as repeating regions, show/hide regions within a string, or little things like inflection (e.g. rendering “{0:N} items” or “{0:N0} item” when arg0 is 1 or not.
I’m happy to see Java (finally) gain a similar feature, but it, like C#,s, seems… limited in its abilities.
Re: JEP 430: String Templates (Preview) Proposed to Target Java 21
#65Earlier quoted context omitted.
Back in 1997, when James Gosling outlined his vision for Java, he said it should be a conservative language (wrapping a very innovative runtime) that would ideally only adopt features that have proven themselves, for some time, in other languages. Being a last mover is at the very core of Java's evolution strategy. It's not playing catch-up because we're not trying to adopt all features other, more "adventurous", lan…
Do you have a link for the 1997 document? The history is surprisingly difficult to explore for being pretty recent.
https://www.win.tue.nl/~evink/education/avp/pdf/feel-of-java...
Re: JEP 430: String Templates (Preview) Proposed to Target Java 21
#66I wonder if annotations and annotation pre-processors could have been an alternate way to approach this had they been applicable to String constants. String name = "Joan"; PreparedStatement query = @SQL "select * from users where firstname = \{name}";
Re: JEP 430: String Templates (Preview) Proposed to Target Java 21
#67It's interesting how C# is always far ahead of Java, they introduced it way earlier, the syntax is simpler, and you can make is safe by using FormattableString as the param type, for example in EF you can do this without worrying about SQL injection: FromSql($"EXECUTE dbo.GetMostPopularBlogsForUser {user}") https://learn.microsoft.com/en-us/ef/core/querying/sql-queri...
Re: JEP 430: String Templates (Preview) Proposed to Target Java 21
#68In swift, there's some nice quasi-laziness you can add to function parameters, so that (say) a logging function that can fully skip evaluating a string sent to it with the `@autoclosure` syntax:
func log(message: @autoclosure () -> String, level: Level = .info) {
guard level >= configuredLevel else {
return
}
actuallyLog(message())
}
And call it like: log(message: "User is \(someExpensiveFunction(user))", level: .debug)
And if the configured log level does not include debug messages, `someExpensiveFunction(user)` doesn't get called.This works because @autoclosure lets you take a parameter that is "function returning String", but callers can just pretend they're passing it a String, without having to decorate it in a function. The compiled code will turn it into a closure behind the scenes, and thus it'll be evaluated lazily.
Not sure if there's any way to do something like this in Java with this proposal...
Re: JEP 430: String Templates (Preview) Proposed to Target Java 21
#69Why oh why is that a backslash!? Over the 9 languages mentioned: 5 languages (inc. JVM ones like groovy and kotlin) are using `$`, 1 language (swift) is using `\`. `\` is a pain to type on many keyboard layouts -- actually most but the US one. It seemed to me that `$` would have been a much more "conventional" choice. This really makes me sad. It looks like the choice was made on purpose to be different.
I assume because `\{` was not a valid escape sequence, which means any use of this character pair can be identified as a template without changing the semantics of existing string literals.
Re: JEP 430: String Templates (Preview) Proposed to Target Java 21
#70One thing I'm not sure is possible in this proposal, is there a way to make the interpolation "lazy", such that the string (and the evaluation of its interpolated components) can be skipped if the string isn't ultimately used? In swift, there's some nice quasi-laziness you can add to function parameters, so that (say) a logging function that can fully skip evaluating a string sent to it with the `@autoclosure` syntax…
void log(Supplier messageSupplier);
log(() -> log.info"User is \{someExpensiveFunction(user)}");
The pattern of using Supplier to provide a lazy argument is pretty well-established afaict.