У меня есть следующая логика в моем коде:
if !@players.include?(p.name)
...
end
@playersэто массив. Есть ли способ, чтобы я мог избежать !?
В идеале этот фрагмент будет:
if @players.does_not_include?(p.name)
...
end
У меня есть следующая логика в моем коде:
if !@players.include?(p.name)
...
end
@playersэто массив. Есть ли способ, чтобы я мог избежать !?
В идеале этот фрагмент будет:
if @players.does_not_include?(p.name)
...
end
Ответы:
if @players.exclude?(p.name)
...
end
ActiveSupport добавляет exclude?метод Array, Hash, и String. Это не чистый Ruby, но используется большим количеством рубинов.
Источник: Active Support Core Extensions (Руководства по Rails)
require 'active_support/core_ext/enumerable'
Ну вот:
unless @players.include?(p.name)
...
end
Вы можете взглянуть на Руководство по стилю Ruby для получения дополнительной информации о подобных методах.
if flag unless @players.include?(p.name)неудобно и if flag && !@players.include?(p.name)использует отрицание.
ifпусть trueпроходит только условие, unlessпропускает falseи nil. Это иногда приводит к трудностям поиска ошибок. Поэтому я предпочитаюexclude?
Как насчет следующего:
unless @players.include?(p.name)
....
end
Глядя только на Ruby:
TL; DR
Для none?передачи используйте блок с ==:
[1, 2].include?(1)
#=> true
[1, 2].none? { |n| 1 == n }
#=> false
Array#include?принимает один аргумент и использует ==для проверки каждого элемента в массиве:
player = [1, 2, 3]
player.include?(1)
#=> true
Enumerable#none?Можно также принять один аргумент, в этом случае он использует ===для сравнения. Чтобы получить противоположное поведение, include?мы опускаем параметр и передаем ему блок, используемый ==для сравнения.
player.none? { |n| 7 == n }
#=> true
!player.include?(7) #notice the '!'
#=> true
В приведенном выше примере мы можем использовать:
player.none?(7)
#=> true
Это потому что Integer#==и Integer#===эквивалентны. Но учтите:
player.include?(Integer)
#=> false
player.none?(Integer)
#=> false
none?возвращается falseпотому что Integer === 1 #=> true. Но действительно законный notinclude?метод должен вернуться true. Итак, как мы делали раньше:
player.none? { |e| Integer == e }
#=> true
module Enumerable
def does_not_include?(item)
!include?(item)
end
end
Хорошо, но если серьезно, то разве работает нормально.
unlessэто нормально для показанного фрагмента, но условие может быть более сложным. Я думаю, что эти отрицательные методы удобно использовать, они допускают более декларативный код.
Используйте unless:
unless @players.include?(p.name) do
...
end
Использование unlessотлично подходит для операторов с одиночными include?предложениями, но, например, когда вам нужно проверить включение чего-либо в одном, Arrayа не в другом, использование include?with exclude?намного удобнее.
if @players.include? && @spectators.exclude? do
....
end
Но, как говорит dizzy42 выше, использование exclude?ActiveSupport требует
Попробуйте, это чистый Ruby, поэтому нет необходимости добавлять какие-либо периферийные платформы
if @players.include?(p.name) == false do
...
end
Я боролся с подобной логикой в течение нескольких дней, и после небольшой проверки нескольких форумов и форумов, посвященных вопросам и ответам, оказалось, что решение было на самом деле довольно простым.
Я искал это для себя, нашел это, а затем и решение. Люди используют запутанные методы и некоторые методы, которые не работают в определенных ситуациях или не работают вообще.
Я знаю, что сейчас слишком поздно, учитывая, что это было опубликовано 6 лет назад, но, надеюсь, будущие посетители найдут это (и, надеюсь, это может очистить их и ваш код).
Простое решение:
if not @players.include?(p.name) do
....
end
doдействительным рубин? я получаю ошибкуsyntax error, unexpected end-of-input(работает, если яdo