safe navigation operator:
tells Ruby to only call the next method if the receiver isn’t nil. Otherwise, the expression returns nil.
class Roster
attr_accessor :players
end
class Player
attr_accessor :name, :position
def initialize(name, position)
@name = name
@position = position
end
end
With these two objects, we can create a roster for a 2-on-2 women’s basketball tournament:
moore = Player.new("Maya Moore", "Forward")
taurasi = Player.new("Diana Taurasi", "Guard")
tourney_roster1 = Roster.new
tourney_roster1.players = [moore, taurasi]
If we want to know the forward for our 2-on-2 team, we might find the name this way:
if tourney_roster1.players.first.position == "Forward"
puts "Forward: #{tourney_roster1.players.first.name}"
end
But what if our opposing roster isn’t set correctly?
tourney_roster2 = Roster.new
if tourney_roster2.players.first.position == "Forward"
puts "Forward: #{tourney_roster1.players.first.name}"
end
tourney_roster2 hasn’t yet been set with any players. The preceding code will raise a NoMethodError because tourney_roster2.players returns nil. We can add conditional statements to avoid this, but it makes our if statement verbose and unclear:
if tourney_roster2.players &&
tourney_roster2.players.first &&
tourney_roster2.players.first.position == "Forward"
Instead, we can use the safe navigation operator to avoid the NoMethodError:
if tourney_roster2.players&.first&.position == "Forward"
puts "Forward: #{tourney_roster1.players.first.name}"
end
Some legitimate use cases: The safe navigation operator comes in handy when working with multiple objects, as shown here, and when chaining methods together.