2011-07-04 9 views
3

私はなぜ関数パラメータとクラスで使用される名前に同じ名前を使用できないのだろうかと思います。以下の例を参照してください。スカラクラス変数名非表示メソッドパラメータ名

scala> class Person() {var name = "bob" } 
defined class Person 

scala> val p = new Person 
p: Person = [email protected] 

scala> p.name 
res0: java.lang.String = bob 

scala> p.name = "alice" 

scala> p.name 
res1: java.lang.String = alice 

scala> def chngName(name:String) = new Person() {this.name= name} 
chngName: (name: String)Person 

scala> val p = chngName("aa") 
p: Person = [email protected] 

scala> p.name 
res2: java.lang.String = bob 

scala> def chngName(n:String) = new Person() {name= n} 
chngName: (n: String)Person 

scala> val p = chngName("aa") 
p: Person = [email protected] 

scala> p.name 
res3: java.lang.String = aa 

もちろん、私は別の名前を使用することができますが、私は、なぜ私はできないか、私はここに欠場しています何かがあるにしたいです。ありがとう

+4

この例では、 'class Person(var name:String =" bob ")'を定義し、bobを得るために 'new Person'を書くか、カスタム名用の新しいPerson( "aa") '。 –

答えて

3

(なぜあなたはchngNameに新しいオブジェクトを返すときvarを使用したいのですか?)

の作品同じ名前のクラスのフィールドはメソッドの引数をシャドウします。

あなたはもちろん、クラスのスコープに入る前に名前を変更できます。このユースケースについて

def chngName(name:String) = { 
    val _name = name 
    new Person() { name = _name } 
} 

を、いくつかの他のオプションは、しかし、があります。ただし、オブジェクトをコピーするかどうかによって異なります。 new Personを返すか、varという簡単な変更で十分です。

完全に新しいオブジェクトを返す場合は、同じセマンティクスと同じ名前のメソッド引数を持つcopyメソッドを追加するcase classメソッドを使用することを検討してください。

case class Person(name: String) 
val p = Person("bob") 
p.name // bob 
val q= p.copy(name = "aa") 
q.name // aa 
q == p // false 
3

new Person()の後に渡されたブロックは、Person初期化ボディに含まれています(必要に応じてコンストラクタ内にあります)。このスコープでは、nameがクラスフィールドとして定義されています。 (したがってnamethis.nameと同じです)。

+0

私はそれほど多くはないと思います。クラスのスコープ外にある関数のパラメータ名をどのように参照するのですか? – thlim

+0

初期化ブロックで私はあなたができるとは思わない。別の名前を付ける必要があります。 BTWは、Jean-Phillipeのコメントをより慣用的な解決策として見ています。 – paradigmatic

-1

意図したとおりに(はるかに少ない簡潔ですが)述べたように、これは、

def chngName(name:String) = {val r = new Person; r.name=name; r;} 
+1

それは質問に焦点を合わせなかった。 –

関連する問題