8

Actualmente estoy escribiendo un compilador Java y he implementado la sección 15.12.2.7. del JLS7 (http://docs.oracle.com/javase/specs/jls/se7/html/jls-15.html#jls-15.12.2.7), una de las secciones más molestas de la especificación. Todavía tengo un problema ya que la especificación de alguna manera parece poco específica o ambigua. Mi problema es esta línea:Inferencia de tipo de método en la especificación Java

lcta (U) =? si el límite superior de U es Objeto, de lo contrario? extends lub (U, Object)

U es una expresión de tipo arbitraria. ¿Cuál es el límite superior de una expresión de tipo? Además, ¿por qué el lcta siempre es un comodín?

La especificación define

CandidateInvocation (G) = lci (Inv (G)).

Ahora, por ejemplo, considere el caso que Inv (G) = {List <String>}, es decir, la única invocación candidata posible es un tipo parametrizado único. Ahora, debido a la regla

lci (G < X1, ..., Xn >) = G < LCTA (X1), ..., LCTA (Xn) >,

el resultado de CandidateInvocation (G) = LCI ({Lista <cadena>}) se definiría como:

Lista < LCTA (String) >

en mi opinión, debería LCTA simp ly return String aquí, porque si List <String> es la única invocación posible, es una buena idea inferir <String> como argumento. Sin embargo, la definición de lcta (U) dicta que el resultado es? o? extiende lub (...), por lo que el resultado ES SIEMPRE un comodín. Esto parece extraño. ¿Qué estoy malinterpretando aquí?

Respuesta

1

He pedido en la lista de correo compilador-dev y recibió la respuesta:

Sí, la especificación está mal aquí. La regla para lcta (U) es simplemente una mierda total :). Además, afirmaron que sería aún mejor no llamar a lcta (U) en absoluto para un único argumento y simplemente usar U (dado que el argumento de tipo menos común de un único argumento U debería ser siempre U mismo).

6

Esto parece un error de la especificación. La cláusula de lcta(U) no existía en JSL3. Aparentemente, la definición de JLS3 de lci(e1..en) está incompleta cuando n=1 y la nueva especificación intenta solucionarlo. Pero la solución parece un galimatías, como usted razonó.

Javac7 calcula lci({ List<String> }) como List<String>, sin tener en cuenta las cláusulas adicionales.

Este problema debe elevarse a los mantenedores de especificaciones; no estoy seguro de cómo contactarlos. Puede probar openjdk compilador-dev lista de correo; hay algunas personas conocedoras de eso.

+0

Ahora he implementado lcta (U) = U que parece funcionar bien. Informaré si encuentro algún caso en el que esta implementación produzca resultados sorprendentes.Por cierto: Is no lub (U, Object) siempre es U, ya que Object es siempre una superclase de U y, por lo tanto, el MEC candidato minimizado y borrado de {U, Object} siempre debe producir U o una de sus subclases? Por lo tanto, la regla es una mierda realmente completa. ¿Lo único por lo que podría ser bueno es transformarse? extiende Objeto a? Sin embargo, dado que U es una expresión de tipo, no puede contener comodines por lo que este caso nunca puede surgir ... realmente extraño. – gexicide

+0

y buena idea con la lista de correo, creo que lo intentaré allí – gexicide

+0

Creo que lub (U, Object) = Objeto – irreputable

Cuestiones relacionadas