Как обозначить аргумент типа для общего полиморфного статического метода в jshell?

в простой Java, я могу написать

class P {
    static <A> A id (A x) { return x; }
    static int y = P.<Integer>id(8);
    static String bar = P.<String>id("foo");
}

в jshell, я могу объявить и использовать id

jshell> <A> A id (A x) { return x; }
|  created method id(A)

jshell> int x = id(8)
x ==> 8

jshell> String y = id("foo")
y ==> "foo"

но я не вижу, как сделать аргумент типа явным.

jshell> String y = <String>id("foo")
|  Error:
|  illegal start of expression
|  String y = <String>id("foo");
|                     ^

Каково имя подразумеваемого контекстного класса?

Где спецификация jshell (часть), которая позволила бы мне ответить на этот вопрос? http://openjdk.java.net/jeps/222 просто упоминает "синтетический класс" в "обертывании". Не похоже, что это можно назвать.

Ответ 1

В действительности ваша ссылка не указывает точный характер (как имя) синтаксического класса, который получает ваши методы как статические методы.

Я попытался получить класс, выполняемый фрагментом с помощью

jshell> new Exception().printStackTrace()
java.lang.Exception
    at REPL.$JShell$17.do_it$($JShell$17.java:8)
    at jdk.internal.reflect.NativeMethodAccessorImpl.invoke0([email protected]/Native Method)
    at jdk.internal.reflect.NativeMethodAccessorImpl.invoke([email protected]/NativeMethodAccessorImpl.java:62)
    at jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke([email protected]/DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke([email protected]/Method.java:531)
    at jdk.internal.jshell.remote.RemoteAgent.commandLoop([email protected]/RemoteAgent.java:124)
    at jdk.internal.jshell.remote.RemoteAgent.main([email protected]/RemoteAgent.java:62)

jshell> Thread.currentThread().getStackTrace()[1].toString()
$15 ==> "do_it$(java:18)"

jshell> Thread.currentThread().getStackTrace()[1].getClassName()
$16 ==> ""

но, как вы можете видеть, информация не находится в трассировке стека.

Самый простой способ обойти его - определить свой метод как статический метод в собственном классе:

jshell> class B { static <A> A id(A x) {return x;} }

Это позволяет вам вызвать

jshell> String y = B.<String>id("foo");

и получает желаемый результат.