web-dev-qa-db-fra.com

Constantes globales dans Groovy

Il est souvent souhaitable de déclarer des constantes en haut d'un script qui peuvent être référencées n'importe où ailleurs dans le script. Dans Groovy, il semble que si vous déclarez une constante en utilisant final, elle n’est pas accessible dans les portées des enfants. Quelle est la solution pour cette exigence très basique et commune? La solution de contournement que j’ai actuellement est de créer une variable non liée, mais ce n’est pas une constante et n’est pas élégante.

44
justGroovy

Groovy n'a pas vraiment de portée mondiale. Lorsque vous avez un script groovy qui ne déclare pas une classe, il est implicitement bloqué dans une classe portant le nom du script. Ainsi, les variables finales de la portée de niveau supérieur ne sont en réalité que des champs de la classe implicite. Par exemple:

// foo.groovy
final MYCONSTANT = "foobar"
println MYCONSTANT

class Helper {
    def hello() { println MYCONSTANT }  // won't work
}
new Helper().hello()

Est plus ou moins équivalent à:

class foo {
    def run() {
        final MYCONSTANT = "foobar"
        println MYCONSTANT
        new Helper().hello()
    }
    static main(args) {
        new foo().run()
    }
}

class Helper {
    def hello() { println MYCONSTANT }  // won't work
}

Il est facile de comprendre pourquoi cela ne fonctionne pas. Un moyen facile de contourner le problème consiste à déclarer vos "globaux" dans une classe fictive appelée par exemple. Constantes, puis effectuez une importation statique dessus. Cela fonctionne même dans un seul script. Exemple:

import static Constants.*

class Constants {
    static final MYCONSTANT = "foobar"
}

println MYCONSTANT

class Helper {
    def hello() { println MYCONSTANT } // works!
}
new Helper().hello()

MODIFIER: 

En outre, les scripts sont un cas particulier. Si vous déclarez une variable sans def ni aucun modificateur tel que final, (c'est-à-dire, utilisez-la simplement), elle passe dans une liaison à l'échelle du script. Donc dans ce cas:

CONSTANT = "foobar"
println "foobar"

CONSTANT est dans la liaison du script, mais dans:

final CONSTANT = "foobar"
println "foobar"

CONSTANT est une variable locale de la méthode run() du script. Pour plus d'informations à ce sujet, rendez-vous sur https://web-beta.archive.org/web/20150108090004/http://groovy.codehaus.org/Scoping+and+the+Semantics+of+%22def%22

75
ataylor

Dans Groovy 1.8+, vous pouvez y parvenir en utilisant l'annotation @Field :

import groovy.transform.Field

@Field final String MY_CONSTANT = 'constant'

def printConstant() { println MY_CONSTANT }

printConstant()
20
bmaupin

Personnellement, je ne le ferais pas, mais techniquement, vous pourriez le faire.

Object.metaclass.MYCONSTANT = 'foobar'

Puis chaque objet l'a

0
Adam Taylor

Un autre moyen efficace d’ajouter les constantes globales au niveau de l’application est Déclarer un interface dans un package approprié en tant que 

interface applicationConstants {
//All constants goes here.
    static final float PI = 3.14 
    String ADMIN_USER = "ADMIN"
    Map languages = [
        "en":   "English",
        "hi":   "Hindi",
        "mr":   "Marathi"

    ]
// Like above you can declare all application level code constants here.

}

Utilisation de constantes dans n'importe quelle classe comme ci-dessous,

 import packageNameContainingInterface.applicationConstants // import statement.
 def adminUser = applicationConstants.ADMIN_USER
 println adminUser
0
Nitin Dhomse