2011-05-01 2 views
9

Si je crée une fonction:def sans args

def a(): String = return "some string" 

le résultat serait « :() String » donc je peux l'utiliser avec/sans parenthèses

D'autre part, si Je crée la même fonction

def a:String = return "some other string" 

il serait juste « un: String » et dans ce cas, je ne peux pas l'utiliser avec des crochets.

Quelle est la différence entre ces deux-là?

+4

Remarque: Vous pouvez omettre le mot-clé 'return' - dans Scala, le résultat d'une méthode est la valeur de la dernière expression de la méthode. – Jesper

+0

Vous pouvez également éviter de spécifier le type def. Je voulais juste souligner que c'est une fonction, pour que tout le monde le voit tout de suite =) – Konstantin

+3

Mais ce n'est pas une fonction - c'est une méthode. :) Et je reçois ceci par le mot-clé 'def', n'est-ce pas? Comme la plupart du temps, 'return' est omis. –

Répondre

10

pratique recommande de définir des fonctions qui ont aucun effet secondaire sans (), et pour ajouter le () à la fois sur le site de la définition et le site d'appel lorsque la fonction a des effets secondaires (par exemple, println() plutôt que println).

6

Si vous définissez a comme ça, sans parenthèses (note, le mot-clé return est pas nécessaire):

def a: String = "some other string" 

puis l'appeler entre parenthèses: a(), le () n'est pas la liste vide d'arguments pour la méthode a; à la place, Scala essayera d'appliquer le () à la chaîne qui renvoie la méthode a. Le message d'erreur que vous obtenez lorsque vous essayez que des conseils que:

scala> a() 
<console>:7: error: not enough arguments for method apply: (n: Int)Char in trait StringLike. 
Unspecified value parameter n. 
     a() 
     ^

Ainsi, dans le second cas, a() signifie quelque chose d'autre que dans le premier cas. Dans le premier cas, cela signifie simplement "appeler a avec une liste d'arguments vide", et dans le second cas cela signifie "appeler a, puis appliquer () au résultat de la méthode", qui échouera sur un String.

éditer Pour développer votre deuxième question dans les commentaires ci-dessous, cela dépend de ce que vous entendez exactement par "la même chose". Comme vous avez vu dans le REPL on dirait qu'il a le type ()java.lang.String tandis que l'autre a le type java.lang.String. Jetez un coup d'œil à ce qui suit, dans lequel x et y tour dans la même chose:

scala> def a() = "aaa" 
a:()java.lang.String 

scala> def b = "bbb" 
b: java.lang.String 

scala> val x = a _ 
x:() => java.lang.String = <function0> 

scala> val y = b _ 
y:() => java.lang.String = <function0> 
+0

Vous pouvez également réduire cette méthode à def a = "some string". Je devrais probablement reformuler ma question. Si je n'essaie pas d'appeler la deuxième fonction avec des crochets, les deux variantes sont la même chose? – Konstantin

+0

Dans le livre "Programmation en Scala, 2ème édition" page 74, il y a un exemple de def sans args. Il dit: "Les parenthèses vides indiquent que la fonction ne prend aucun paramètre" (parenteses en résultat d'interprète de scala). Ils sont suivis du type def. L'interprète de Scala dit aussi que les defs sont égaux. La chose que je ne comprends pas est pourquoi la deuxième notation ne comprend pas la chose de parenthèse =) C'est bizarre – Konstantin