2011-08-23 8 views
7

Мне, должно быть, здесь не хватает чего-то глупого. У меня есть это:scala case class equals (==) не работает должным образом

case class Color(val rgb:Int) { 
    private val c = rgb - 0xff000000 
    val r = (c & 0xff0000) >> 16 
    val g = (c & 0x00ff00) >> 8 
    val b = (c & 0x0000ff) 
} 

case object Red extends Color(0xffff0000) 
case object Green extends Color(0xff00ff00) 
case object Blue extends Color(0xff0000ff) 

Тогда я ожидаю, что это напечатать истинную:

val c = Color(0xff00ff00) 
println(c == Green) 

Почему не так ли ??

+1

Другой совет: 'val' в аргумент' Color' является излишним, так как 'Color' случай класса. Достаточно сказать: 'case class Color (rgb: Int)' –

+0

Да, это было последнее дополнение, поскольку я пытался заставить его работать так, как я ожидал; теперь, когда вы упомянули об этом, я помню, что это не нужно. –

ответ

13

Классы классов (или объекты), наследующие классы case, являются плохой практикой и являются незаконными по сравнению с Scala 2.9.1. Используйте object вместо case object для определения Red, Green и Blue.

+3

case object create 'equals',' hashcode' и 'apply/unapply'. Почему это плохая практика? –

+2

@Amir Raminfar: Нет, на самом деле этого не происходит, потому что методы, уже существующие в 'Color' и' case', только создают эти методы, если они еще не переопределены. @ 4e6: неважно, используете ли вы объект 'object' или' case object ', если вы все еще наследуете класс case! –

+0

А вы имеете в виду подкласс класса case. Я думаю, вы должны изменить формулировку, потому что это звучит так, как будто вы говорите, что использование «случайных объектов» вообще плохо. –

0

Почему должен соответствовать? Зеленый - это объект-компаньон, c - экземпляр. Они не равные.

+0

Это ошибка с наследованием от случая к случаю, которая теперь незаконна. Код работает, когда модификатор case удаляется из объектов, потому что определение '==' на классах классов проверяет равенство аргументов (здесь, 'rgb'). Кстати, «Зеленый» не является компаньоном для класса «Цвет». Сопутствующий объект должен иметь то же имя, что и trait/class, и (я думаю) должен быть определен в том же файле. Дополнительная информация о том, почему полезны вспомогательные объекты: http://stackoverflow.com/questions/609744/what-is-the-rationale-behind-having-companion-objects-in-scala –

0

Я думаю, что это был соответствующий вопрос: «Почему класс объекта и класс case, который он расширяет, не равны».

Использование Scala 2.12.2

Я добавил следующие строки в вашем примере и теперь объект равен экземпляру класса.

object Black extends Color(0x00000000) 
val black1 = Color(0x00000000) 
black1 == Black 

res1: Boolean = TRUE

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