Scala конструктор без параметров

У меня может быть глупа проблема... Я не могу понять, как сделать конструктор без параметров в Scala. Я знаю, что могу просто написать все это в классе (особенно потому, что это единственный конструктор, который мне нужен), но это не совсем правильно.

Что у меня:

    class Foo {
        //some init code

        //...
    }

Что бы я хотел (но не работает, поскольку он хочет, чтобы я сначала вызывал другой конструктор):

    class Foo {
        // The only constructor
        def this() = { 
            //some init code
        }

        //...
    }

Ответ 1

Все классы в Scala имеют первичный конструктор и необязательно некоторые вспомогательные конструкторы (которые должны относиться к основному конструктору или другому вспомогательному конструктору).

В вашем случае проблема заключается в том, что в обоих случаях вы определили первичный конструктор как отсутствие аргументов, а затем во втором случае вы попытаетесь определить вспомогательный конструктор с той же сигнатурой. Это не работает по той же причине, что и следующее:

// Primary constructor takes a String
class Foo(s: String) {
    // Auxiliary constructor also takes a String?? (compile error)
    def this(a: String) {
        this(a)
    }
}

Это не связано с тем, что конструктор не является args; следующие компиляции, например:

class Foo(s: String) {
    // alternative no-arg constructor (with different signature from primary)
    def this() {
        this("Default value from auxiliary constructor")
    }
}

В частности, во втором примере ваш комментарий "единственный конструктор" неверен. Вспомогательные конструкторы всегда вторичны для основного конструктора и никогда не могут быть единственным конструктором.

FWIW, первый пример - это единственный вариант, открытый для вас, но он выглядит хорошо для меня. Если вы только начали использовать Scala, я уверен, что он начнет чувствовать себя достаточно скоро - и важно избегать способов Java-esque делать вещи, когда есть более идиоматические альтернативы.

Ответ 2

Для чего вы можете добавить дополнительную область для "отметки" кода инициализации.

class Foo {
   {
      // init code here
   }
}

Ответ 3

Вставка кода инициализации в тело класса - единственный способ иметь конструктор без параметров. Я полагаю, если вы хотите, чтобы вы могли сделать что-то вроде:

class Foo {

  private def init {
    //init code here
  }

  init()
}

который как можно ближе к вам.

Ответ 4

Код инициализации является телом метода. Но вы можете это сделать, если это вас сильно беспокоит:

class Foo {
        locally { 
            //some init code
        }
}