2010-08-09 11 views
212

Un uso de la palabra clave var en C# es una declaración de tipo implícita. ¿Cuál es la sintaxis equivalente de Java para var?¿Cuál es el equivalente de la palabra clave 'var' de C# en Java?

+4

'val' (o' var') si se utiliza un lenguaje particular "reemplazo de Java" ;-) –

+6

@pst: que sería Scala? Hm sí, lo es. – rsenna

+0

Para IntelliJ, presenté esto como una solicitud de función: http://youtrack.jetbrains.com/issue/IDEA-102808 El IDE podría colapsar el código para mostrar val o var aunque el código subyacente no lo tenga. –

Respuesta

212

No hay ninguno. Por desgracia, tienes que escribir el nombre completo.

Editar 6 años después de haber sido publicado, para recoger algunos de los comentarios de abajo:

  • La razón C# tiene la palabra clave var se debe a que es posible tener tipos que no tienen nombre en .NET. Por ejemplo:

    var myData = new { a = 1, b = "2" }; 
    

    En este caso, sería imposible dar un tipo adecuado para myData. Hace 6 años, esto era imposible en Java (todos los tipos tenían nombres, incluso si eran extremadamente detallados y poco sofisticados). No sé si esto ha cambiado mientras tanto.

  • var no es lo mismo que dynamic. var Iiables todavía están 100% estáticamente tipados. Esto no va a compilar:

    var myString = "foo"; 
    myString = 3; 
    
  • var también es útil cuando el tipo es evidente a partir del contexto. Por ejemplo:

    var currentUser = User.GetCurrent(); 
    

    me puede decir que en cualquier código que soy responsable de, currentUser tiene una clase User o que se derivan de ella. Obviamente, si su implementación de User.GetCurrent devuelve un int, entonces tal vez esto sea perjudicial para usted.

  • Esto no tiene nada que ver con var, pero si usted tiene jerarquías de herencia extraños donde remedar métodos con otros métodos (por ejemplo new public void DoAThing()), no se olvide que los métodos no virtuales se ven afectados por el tipo que se presentan como .

    no puedo imaginar un escenario real mundo donde esto es indicativo de un buen diseño, pero esto puede no funcionar como se esperaba:

    class Foo { 
        public void Non() {} 
        public virtual void Virt() {} 
    } 
    
    class Bar : Foo { 
        public new void Non() {} 
        public override void Virt() {} 
    } 
    
    class Baz { 
        public static Foo GetFoo() { 
         return new Bar(); 
        } 
    } 
    
    var foo = Baz.GetFoo(); 
    foo.Non(); // <- Foo.Non, not Bar.Non 
    foo.Virt(); // <- Bar.Virt 
    
    var bar = (Bar)foo; 
    bar.Non(); // <- Bar.Non, not Foo.Non 
    bar.Virt(); // <- Still Bar.Virt 
    

    Como se ha indicado, los métodos virtuales no se ven afectados por esto.

  • No, no hay una forma no torpe de inicializar un var sin una variable real.

    var foo1 = "bar";  //good 
    var foo2;    //bad, what type? 
    var foo3 = null;   //bad, null doesn't have a type 
    var foo4 = default(var); //what? 
    var foo5 = (object)null; //legal, but go home, you're drunk 
    

    En este caso, basta con hacerlo de la manera antigua:

    object foo6; 
    
+1

Y para ser justos también; 1. solo es reciente en C#, por lo que Arturo no puede culpar a los "creadores" y 2. solo se debe a otras características que no estaban en el 1.0 de ninguno de los dos idiomas, que se convierta en una idea que es útil en lugar de una gran forma de hacer código menos claro y más propenso a errores. Es necesario en C# 3.0, y tendría algunos casos útiles en C# 2.0, pero hubiera sido algo malo en C# 1.0. –

+1

@Mike Caron: y debido a ciertos tipos muy largos (sin 'var', eso haría a Linq prácticamente inutilizable). – rsenna

+0

@pst ¿Qué tiene que ver la tipificación implícita con el polimorfismo? La palabra clave 'var' es 100% idéntica a la declaración de una variable con el tipo exacto de la expresión. Eso es todo. –

36

Si se agrega a su proyecto Lombok puedes es val palabra clave.

http://projectlombok.org/features/val.html

+1

@rightfold: Objetos cuya referencia es 'final' no son necesariamente inmutables. Considere 'final StringBuilder strB = new StringBuilder (" Mi referencia es final "); strB.append ("No soy inmutable"); ' –

+1

Desde lombok v1.16.12 también hay soporte experimental para' var'. https://projectlombok.org/features/experimental/var.html –

+0

@MatthiasBraun su ejemplo es incorrecto. En este caso, la clase StringBuilder es inmutable, solo agrega valor de cadena a su estructura interna mediante el método, esto es totalmente legal. –

19

he cocinado un plugin para IntelliJ que – – de una manera que da var en Java.Es un truco, por lo que se aplican los descargos de responsabilidad habituales, pero si utiliza IntelliJ para su desarrollo de Java y desea probarlo, está en https://bitbucket.org/balpha/varsity.

+0

Sería genial tener un atajo de teclado para doblar/desplegar tipos de declaración en el editor actual. Gran plugin sin embargo. – hotkey

+2

@hotkey Esto utiliza el plegado de código incorporado de IntelliJ, para que pueda desplegar todo con Ctrl-Shift-NumPadPlus. Cuando el cursor está en una línea que contiene una declaración de variable plegada, puede Ctrl-NumPadPlus y Ctrl-NumPadMinus para plegar/desplegar las declaraciones en el método actual. Plegar todas las declaraciones es un poco incómodo, tienes que doblar todo (Ctrl-Shift-NumPadMinus) y luego desplegar todo de nuevo (Ctrl-Shift-NumPadPlus). – balpha

7

Una solución simple (suponiendo que esté utilizando un IDE decente) es simplemente escribir 'int' en todas partes y luego hacer que establezca el tipo para usted.

De hecho, acabo de agregar una clase llamada 'var' para que no tenga que escribir algo diferente.

El código sigue siendo demasiado detallado, pero al menos no tiene que escribirlo.

+0

¿Cuándo dices "IDE decente" está excluido Eclipse *? - Esto no parece funcionar en Luna (al menos cuando lo intenté con 'int') - ¿Me falta algo? (*: aunque nunca llamaría a Eclipse IDE decente, no puedo juzgar por los demás ...) – BrainSlugs83

+0

@ BrainSlugs83 dunno Estoy usando IDEA, eclipse no realmente usado anteriormente. ¿No corrige los tipos por ti? Estoy acostumbrado a C#/visual studio/resharper, que es como IDEA, ¡excepto que realmente funciona correctamente! En todos los jetbrains, puedes presionar alt-enter para obtener una lista de sugerencias cuando hay un error, por lo que establecer el tipo en int introduce un error en el que puedes ingresar y ordenar el tipo –

3

Sé que esto es más antiguo, pero ¿por qué no crear una clase var y crear constructores con diferentes tipos y dependiendo de qué constructores se invoque se obtiene var con diferente tipo. Incluso podría crear métodos para convertir un tipo en otro.

5

Puede echar un vistazo a Kotlin por JetBrains, pero es val. no var.

+3

Kotlin tiene val y var. val es equivalente a declarar una variable final en java, var permite la reasignación. – samlewis

10

PEC - JDK Enhancement-Propuesta

http://openjdk.java.net/jeps/286

PEC 286: Local-Variable Tipo Inferencia

autor Brian Goetz

// Goals: 
var list = new ArrayList<String>(); // infers ArrayList<String> 
var stream = list.stream();   // infers Stream<String> 
+0

¿Qué versión de Java? 10? –

+1

Lectura relacionada: [Primer contacto con 'var' en Java 10] (https://blog.codefx.org/java/java-10-var-type-inference/) –

2

Lombok supports var pero sigue siendo clasificado como experimental:

import lombok.experimental.var; 

var number = 1; // Inferred type: int 
number = 2; // Legal reassign since var is not final 
number = "Hi"; // Compilation error since a string cannot be assigned to an int variable 
System.out.println(number); 

Here es una trampa que debe evitarse al intentar usarlo en IntelliJ IDEA. Parece que funciona como se esperaba, aunque incluye autocompletar y todo. Hasta que exista una solución "no hacky" (por ejemplo, debido a JEP 286: Local-Variable Type Inference), esta podría ser su mejor apuesta en este momento.

Tenga en cuenta que val también es compatible con Lombok sin modificar ni crear un lombok.config.

0

Se admitirá en JDK 10. Incluso es posible verlo en acción en el early access build.

El JEP 286:

realzar el lenguaje Java para extender la inferencia de tipos de declaraciones de variables locales con inicializadores.

Así que ahora en lugar de escribir:

List<> list = new ArrayList<String>(); 
Stream<> stream = myStream(); 

Usted escribe:

var list = new ArrayList<String>(); 
var stream = myStream(); 

Notas:

  • var es ahora una palabra clave reservada
  • Java es todavía compromiso con la tipa estática!
  • Es solamente se pueden utilizar en las declaraciones de variables locales
Cuestiones relacionadas