Friday, 30 July 2010

5 + 1 главных особенностей, которые необходимо знать о конструкторах в Scala




Вольный перевод данного поста: Top 5 Things to Know About Constructors in Scala и плюс ещё одна особенность, на которую волей случая наткнулся.

Я играюсь со Scala в течение нескольких месяцев, и одной из вещей, с котороми пришлось бороться после перехода с Java были конструкторы. Они похожи на конструкторы в Java, но синтаксис имеет отличия.
Что бы помочь вам быстрее начать пользоваться Scala, приведу пять основных особенностей связанных с конструкторами. Начнём:

1. Как сделать конструктор с параметром?
public class Foo() {
  public Bar bar;
  public Foo(Bar bar) { 
    this.bar = bar; 
  }
}
На Scala это будет выглядеть так:
class Foo(val bar:Bar)
В данном случае val создаёт неизменяемое публичное поле, используте var для создание изменяемых полей.

2. Как сделать приватные поля?
public class Foo() {
  private final Bar bar;
  public Foo(Bar bar) { 
    this.bar = bar; 
  } 
}
На Scala это будет выглядеть так:
class Foo(private val bar: Bar)
Приватные поля не так необходимы как в Java и вы можете делать все поля публичными. В случае необходимости вы можете потом определить геттер и сеттер без внесения изменений в клиенты.

3. Как использовать super()?
public class Foo() extends SuperFoo {
  public Foo(Bar bar) { 
    super(bar); 
  } 
}
На Scala это будет выглядеть так:
class Foo(bar:Bar) extends SuperFoo(bar)b

4. Как создать более одного конструктора?
public class Foo {
  public Bar bar;
  public Foo() { 
    this(new Bar()); 
  } 
  public Foo(Bar bar) { 
    this. bar = bar;
  } 
}
На Scala это будет выглядеть так:
class Foo(val bar:Bar) {
  def this() = this(new Bar)
}
Второй конструктор (this()) делегирует свои обязанности другому конструктору.

5. Как сделать "bean style" геттер и сеттер?
public class Foo() {
  private Bar bar; 
  public Foo(Bar bar) { 
    this.bar = bar; 
  } 
  public Bar getBar() { 
    return bar; 
  } 
  public void setBar(Bar bar) { 
    this.bar = bar;
  }
}
На Scala это будет выглядеть так:
class Foo(@BeanProperty var bar:Bar)
Поле bar является публичным, что не представляет проблем в Scala (смотри выше).

(далее от переводчика)
6. Как сделать конструктор c несколькими выражений?
Данный пункт отмечен в примечание к посту, но я покажу его подробнее.

public class Foo() {
  private Int b; 
  private Int y; 
  public Foo(Int b) { 
    this.b = b; 
  } 
  public Foo() { 
    this.y = java.util.Random.nextInt();
    this.y += 1;
    this.b = b; 
  } 
}

На Scala это будет выглядеть так:

class Foo (val b:Int) {
  var y = 0
  def this() = {
    this(3)
    y = scala.util.Random.nextInt
    y += 1
  }
}
Язык Scala накладывает ограничение на метод this(): "- первым вызовом конструктора должен быть вызов другого конструктора, причем любого - важно только чтобы цепочка вызовов конструкторов в итоге привела к вызову первичного конструктора"
Спасибо javverwocky, за указание на ошибку и пример.




3 comments:

  1. 6. Как сделать конструктор c несколькими выражений?

    ReplyDelete
  2. >Язык Scala накладывает ограничение на метод this(), и требует что бы он состоял из одного выражения.

    Нет такого ограничения, можете попробовать сами вот такой код:

    class Foo (val b:Int) {
    var y = 0
    def this() = {
    this(3)
    y = scala.util.Random.nextInt
    y += 1
    }
    }

    Единственное ограничение - первым вызовом конструктора должен быть вызов другого конструктора, причем любого - важно только чтобы цепочка вызовов конструкторов в итоге привела к вызову первичного конструктора.

    ReplyDelete
  3. 2 javverwocky
    Благодарю, поправил.

    ReplyDelete