2010-02-14 7 views
19

[Más adelante: todavía no se puede determinar si Groovy tiene tipado estático (parece que no) o si el bytecode generado mediante tipado explícito es diferente (parece que sí). De todos modos, a la pregunta]Mecanografía explícita en Groovy: ¿a veces o nunca?

Una de las principales diferencias entre Groovy y otros lenguajes dinámicos - o al menos Ruby - es que puedes estáticamente escribir variables explícitamente cuando lo desees.

Dicho esto, ¿cuándo se debe usar el tipado estático en Groovy? Aquí hay algunas posibles respuestas que se me ocurren:

  1. Solo cuando hay un problema de rendimiento. Statically typed variables are faster in Groovy. (o son? Algunas preguntas sobre este enlace)
  2. En las interfaces públicas (métodos, campos) para las clases, por lo que obtiene autocompletar. ¿Es esto posible/verdadero/totalmente incorrecto?
  3. Nunca, solo complica el código y frustra el propósito de usar Groovy.
  4. Sí cuando sus clases se heredan o se utilizan

no sólo estoy interesado en lo que haces, pero es más importante lo que has visto en torno a proyectos codificados en Groovy. ¿Cuál es la norma?

Nota: Si esta pregunta es de alguna manera incorrecta o se pierde algunas categorías de estática-dinámica, hágamelo saber y lo arreglaré.

+0

Creo que el título debería ser "tipos explícitos en groovy" ya que no hay tipeo estático en el idioma –

+0

@Pablo Fernandez, cambió la pregunta un poco. –

Respuesta

16

En mi experiencia, no hay ninguna norma. Algunos tipos de uso mucho, algunos nunca los usan. Personalmente, siempre trato de usar tipos en mis firmas de métodos (para params y valores devueltos). Por ejemplo, yo siempre escribo un método como este

Boolean doLogin(User user) { 
// implementation omitted 
} 

A pesar de que podría escribir como este

def doLogin(user) { 
// implementation omitted 
} 

hago esto por estas razones:

  1. Documentación: otros desarrolladores (y yo mismo) sé qué tipos serán provistos y devueltos por el método sin leer la implementación
  2. Tipo Seguridad: aunque Groovy no tiene comprobaciones en tiempo de compilación, si llamo a la versión estáticamente tipada de doLogin con un parámetro que no es de usuario, fallará inmediatamente, por lo que es probable que el problema sea fácil de solucionar.Si llamo a la versión de tipo dinámico, fallará después de el método se invoca, y la causa de la falla puede no ser inmediatamente obvia.
  3. Código de finalización: esto es particularmente útil cuando se utiliza un buen IDE (es decir, IntelliJ), ya que incluso puede proporcionar la terminación para los métodos añadidos dinámicamente tales como la clase de dominio buscadores dinámicos

También uso tipos bastante poco dentro de la implementación de mis métodos por las mismas razones. De hecho, las únicas veces que no uso tipos son:

  1. Realmente quiero admitir una amplia gama de tipos. Por ejemplo, un método que convierte una cadena en un número también puede encubrir una colección o matriz de cadenas en los números
  2. ¡Pereza! Si el alcance de una variable es muy corto, ya sé qué métodos quiero llamar, y no tengo la clase ya importada, y luego declaro que el tipo parece ser más problemático de lo que vale.

Por cierto, no confiaría demasiado en esa publicación de blog que ha vinculado para afirmar que escribió Groovy es mucho más rápido que Groyvy sin tipo. Nunca había escuchado eso antes, y no encontré la evidencia muy convincente.

+0

Gran respuesta, gracias Don.No sé acerca de esa publicación de blog, pero si tengo algo de tiempo para hacer algunos puntos de referencia, volveré a publicar aquí. Me parece razonable, y creo que el bytecode depende de cómo especifiques las variables. –

+1

1.5 años después, estoy trabajando en Objective-C, que es básicamente idéntico a groovy (despacho dinámico, tipos solo en tiempo de compilación), y LA MAYORÍA DE PERSONAS TRABAJA CON TIPOS TANTO POSIBLE, que está en línea con la forma en que trabajo y generalmente una buena idea. –

0

Groovy no admite el tipado estático. Véalo usted mismo:

public Foo func(Bar bar) { 
    return bar 
} 
println("no static typing") 

Guarde y compile ese archivo y ejecútelo.

+0

El archivo se ejecutará, pero si intenta pasar un no-Bar a la función, dará una 'groovy.lang.MissingMethodException: No firma del método:' –

+0

que está en __runtime__ Creo –

+0

No estoy seguro, Pablo: Tengo entendido que el bytecode producido por Groovy es diferente si usa los tipos o si no lo hace. –

1

He visto información tipo utilizada principalmente en clases de servicio para métodos públicos. Dependiendo de cuán compleja sea la lista de parámetros, incluso aquí suelo ver solo el tipo de devolución escrito. Por ejemplo:

class WorkflowService { 
    .... 
    WorkItem getWorkItem(processNbr) throws WorkflowException { 
     ... 
     ... 
    } 
} 

creo que esto es útil porque nos dice explícitamente que el usuario del servicio de qué tipo serán tratando y ayuda con el asistente de código en el IDE de.

+0

Gracias por eso, eso también es mi pensamiento –

2

trabajé en un varios proyectos maravillosos y nos limitamos a estos convenios:

  • Todos los tipos de métodos públicos deben ser especificadas.

    public int getAgeOfUser (cadena usuario) {} ...

  • Todas las variables privadas se declaran usando la palabra clave def .

Estas convenciones le permiten lograr muchas cosas.

En primer lugar, si usa la compilación conjunta, su código java podrá interactuar fácilmente con su código Groovy. En segundo lugar, tales declaraciones explícitas hacen que el código en proyectos grandes sea más legible y sostenible. Y la autocompleción de curso también es un beneficio importante.

Por otro lado, el alcance de un método suele ser bastante pequeño, por lo que no es necesario declarar explícitamente los tipos. Por cierto, los IDE modernos pueden completar automáticamente sus variables locales incluso si usa defs.

+0

Muy interesante. ¿Cuál es la ventaja de usar def para vars privados en lugar de solo declarar el tipo? Tú lo sabes de todos modos y Groovy no te obligará a lanzar. –

+1

Si tiene un ámbito local, conoce el tipo de variable y se ve mejor. Por ejemplo: 'fábrica def = PersonContactFactory.newInstance()' se ve un poco más claro que: ' contacto PersonContactFactory = PersonContactFactory.newInstance()' Esta es la única razón por la que prefiero usar en defs un alcance local. De todos modos, su IDE conoce el tipo de su variable y no tiene ninguna comprobación estática. –

Cuestiones relacionadas