2015-04-27 2 views
3

Попытка получить знания и навыки Scala, вот простой пример. Я хочу определить класс, который определяет множество операций, которые могут быть реализованы множеством способов. Я мог бы начать с того,Правильное использование черт и объектов Scala

sealed trait Operations{ 
    def add 
    def multiply 
} 

Так, например, я мог бы создать экземпляр этого класса с объектом означает, что add и multiply очень толково,

case object CorrectOperations extends Operations{ 
    def add(a:Double,b:Double)= a+b 
    def multiply(a:Double,b:Double)= a*b 
} 

А также, могут быть и другие способы определения тех операции, такие как, очевидно, неправильный путь,

case object SillyOperations extends Operations{ 
    def add(a:Double,b:Double)= a + b - 10 
    def multiply(a:Double,b:Double)= a/b 
} 

Я хотел бы передать такой экземпляр в функцию, которая будет выполнять операции в частности.

def doOperations(a:Double,b:Double, op:operations) = { 
    op.multiply(a,b) - op.add(a,b) 
} 

Я хотел бы doOperations взять любой объект типа operations, так что я могу использовать в add и multiply, какими бы они ни были.

Что мне нужно изменить примерно doOperations, и что я здесь непонимаю? Спасибо

+0

Пахнет как coursera здесь. –

ответ

5

Не запустите свой код, но я полагаю, у вас есть ошибка компиляции.

Если вы не определяете подпись методов в признаке Operations, то по умолчанию оно будет интерпретировано как () => Unit.

Это означает, что методы в наследующих объектах не очень главенствующая методы в черте, но определить перегрузок вместо этого. Подробнее об этом here. Это можно проверить, написав override перед определениями методов в методах объектов. Это заставит компилятор явно предупредить вас о том, что методы не переопределяют ничего из черты предка и работают как «защитная сетка» от подобных ошибок.

Чтобы исправить ошибку, изложить подпись признака как следующее:

sealed trait Operations{ 
    def add(a:Double,b:Double):Double 
    def multiply(a:Double,b:Double):Double 
} 

В самом деле, типы параметров вывода даже не нужно в методах работы наследующих объектов (но обратите внимание на добавленную override):

case object CorrectOperations extends Operations{ 
    override def add(a:Double,b:Double) = a+b 
    override def multiply(a:Double,b:Double) = a*b 
} 
+1

Спасибо! Поэтому ваш второй блок кода там не работает для меня, 'override def add = a + b', кажется, мне все еще нужны подписи ... – keegan

+1

@keegan извините, действительно, вы правы, ему нужны входные параметры .. но не выход. См. Отредактированную версию. –

Смежные вопросы