Вот как я могу проверить, является ли число четным / нечетным в Ruby:
def even_or_odd(number)
['Even', 'Odd'][number % 2]
end
Ближайшее, что у меня есть в Scala, это следующее:
def evenOrOdd(number: Int): String = {
val a = Array("Even", "Odd")
a(number % 2)
}
Я действительно хочу сделать что-то вроде этого, но он не компилируется:
def evenOrOdd(number: Int): String = {
("Even", "Odd")(number % 2)
}
Во-первых, как называется этот тип «анонимной» структуры? Во-вторых, как это элегантно использовать? Если у вас есть аналогичный пример, иллюстрирующий мощь / лаконичность / ясность Scala, я бы хотел его увидеть.
Я понимаю. Это тривиальный пример, подчеркивающий мою проблему. Я планирую использовать эту конструкцию там, где в плохо написанных программах есть несколько операторов if-then, перемежающихся литералами. В моем бизнесе краткость и ясность имеют прямое влияние на прибыльность. Философ может справедливо возразить, что они субъективны, но красота в глазах смотрящего, и мои коллеги на нее проницательны.
Языки программирования - это инструменты. Вы можете думать о них как о различных видах транспорта. У вас есть велосипеды, автомобили, автобусы, грузовики, трейлеры, поезда, телеги, лошади. Каждый из них может привести вас в разные места, но отличается друг от друга, и у каждого есть свои сильные и слабые стороны. Сейчас эстетики сильно отличаются друг от друга. conciseness и clarity - это хорошо, но я каждый раз буду выбирать correctness над ними обоими.
Это взлом. Более того, он выдаст ошибку при отрицательных нечетных числах, поскольку -1 % 2 оценивается как -1 в Scala, Java, JavaScript и, возможно, в некоторых других. Просто используйте if (number % 2 == 0) "even" else "odd". Легче читать и работает.
Брайан, если вы хотите увидеть оригинальный хак, взгляните на это: stackoverflow.com/questions/51126534/fizzbuzz-ruby-one-liner. Руби умеет работать с отрицательными индексами. Это может быть полезно с индексами, основанными на расчетах. К сожалению, Scala и Java не делают отрицательных индексов. На мой взгляд, это слабость.



Это компилирует:
def evenOrOdd(number: Int): String = {
Array("Even", "Odd").apply(number % 2)
}
В большинстве случаев вызов метода apply можно опустить, поскольку он имеет синтаксический сахар. Однако в этом случае это не сработает. Вам нужно либо извлечь Array("Even", "Odd") в var, var или def, либо отказаться от синтаксического сахара.
Причину, по которой синтаксический сахар Array("Even", "Odd")(number % 2) не работает, как-то сложно объяснить, но это вызвано следующим:
new T[], где T - универсальный тип)ClassTag в Array.apply; ClassTag поставляется со своим собственным синтаксическим сахаром, что делает Array("Even", "Odd")(number % 2) недействительным.("Even", "Odd") относится к типу (String,String), который является псевдонимом для Tuple2[String, String], его вспомогательными устройствами являются ._1 и ._2.
ты мог бы сделать или
Обновлено: как указано в комментариях, это на самом деле не сработает. Это будет, хотя Array("Even", "Odd")(number % 2)Array("Even", "Odd").apply(number % 2)
number % 2 match {
case 0 => "Even"
case 1 => "Odd"
case -1 => "Odd" //EDIT: as per comment. I forgot about this case
}
Array("Even", "Odd")(number % 2) не компилируется. Это как-то связано с параметром типа ClassTag, но я не могу предоставить более подробную информацию по этому поводу.
да ты правый странный. например Array(1,2)(4 % 2) работает как положено Подредактирую. Благодарность!
Vector("Even", "Odd")(number % 2) компилируется.
Ваш пример не работает с отрицательными числами. Вам, вероятно, следует изменить второй регистр на _
def evenOrOdd(number: Int) =
List("Even","Odd")(number % 2)
Что ж ... такие варианты использования никоим образом не показывают «мощь» языка. И
conciseness, иclarityочень субъективны к пользователю. Сила Scala заключается в ее системе типов и функциональных возможностях.