¿Qué es el operador Ruby<=>(nave espacial)?
operators comparison-operators (6)
¿Qué es
<=>(el operador ''Spaceship'')
De acuerdo con el RFC que introdujo al operador , $ a <=> $ b
- 0 if $a == $b
- -1 if $a < $b
- 1 if $a > $b
- Return 0 if values on either side are equal
- Return 1 if value on the left is greater
- Return -1 if the value on the right is greater
Ejemplo:
//Comparing Integers
echo 1 <=> 1; //ouputs 0
echo 3 <=> 4; //outputs -1
echo 4 <=> 3; //outputs 1
//String Comparison
echo "x" <=> "x"; // 0
echo "x" <=> "y"; //-1
echo "y" <=> "x"; //1
MÁS:
// Integers
echo 1 <=> 1; // 0
echo 1 <=> 2; // -1
echo 2 <=> 1; // 1
// Floats
echo 1.5 <=> 1.5; // 0
echo 1.5 <=> 2.5; // -1
echo 2.5 <=> 1.5; // 1
// Strings
echo "a" <=> "a"; // 0
echo "a" <=> "b"; // -1
echo "b" <=> "a"; // 1
echo "a" <=> "aa"; // -1
echo "zz" <=> "aa"; // 1
// Arrays
echo [] <=> []; // 0
echo [1, 2, 3] <=> [1, 2, 3]; // 0
echo [1, 2, 3] <=> []; // 1
echo [1, 2, 3] <=> [1, 2, 1]; // 1
echo [1, 2, 3] <=> [1, 2, 4]; // -1
// Objects
$a = (object) ["a" => "b"];
$b = (object) ["a" => "b"];
echo $a <=> $b; // 0
¿Qué es el operador Ruby <=> (nave espacial)? ¿El operador está implementado por otros idiomas?
Dado que este operador reduce las comparaciones a una expresión entera, proporciona la manera más general de ordenar ascendente o descendente en función de múltiples columnas / atributos.
Por ejemplo, si tengo una variedad de objetos, puedo hacer cosas como esta:
# `sort!` modifies array in place, avoids duplicating if it''s large...
# Sort by zip code, ascending
my_objects.sort! { |a, b| a.zip <=> b.zip }
# Sort by zip code, descending
my_objects.sort! { |a, b| b.zip <=> a.zip }
# ...same as...
my_objects.sort! { |a, b| -1 * (a.zip <=> b.zip) }
# Sort by last name, then first
my_objects.sort! { |a, b| 2 * (a.last <=> b.last) + (a.first <=> b.first) }
# Sort by zip, then age descending, then last name, then first
my_objects.sort! do |a, b|
4 * (a.zip <=> b.zip) +
-3 * (a.age <=> b.age) +
2 * (a.last <=> b.last) +
(a.first <=> b.first)
end
Este patrón básico puede generalizarse para ordenarse por cualquier número de columnas, en cualquier permutación de ascendente / descendente en cada una.
El método de la nave espacial es útil cuando lo define en su propia clase e incluye el módulo Comparable . Entonces tu clase obtiene el >, < , >=, <=, ==, and between? Métodos de forma gratuita.
class Card
include Comparable
attr_reader :value
def initialize(value)
@value = value
end
def <=> (other) #1 if self>other; 0 if self==other; -1 if self<other
self.value <=> other.value
end
end
a = Card.new(7)
b = Card.new(10)
c = Card.new(8)
puts a > b # false
puts c.between?(a,b) # true
# Array#sort uses <=> :
p [a,b,c].sort # [#<Card:0x0000000242d298 @value=7>, #<Card:0x0000000242d248 @value=8>, #<Card:0x0000000242d270 @value=10>]
Es un operador de comparación general. Devuelve un -1, 0 o +1 dependiendo de si su receptor es menor, igual o mayor que su argumento.
Perl fue probablemente el primer idioma para usarlo. Groovy es otro lenguaje que lo soporta. Básicamente, en lugar de devolver 1 ( true ) o 0 ( false ) dependiendo de si los argumentos son iguales o desiguales, el operador de la nave espacial devolverá 1 , 0 o −1 dependiendo del valor del argumento de la izquierda en relación con el argumento de la derecha.
a <=> b :=
if a < b then return -1
if a = b then return 0
if a > b then return 1
if a and b are not comparable then return nil
Es útil para ordenar una matriz.
Te explicaré con un simple ejemplo.
[1,3,2] <=> [2,2,2]Ruby comenzará a comparar cada elemento de ambas matrices desde el lado izquierdo.
1para la matriz izquierda es más pequeño que2de la matriz derecha. Por lo tanto, la matriz izquierda es más pequeña que la derecha. La salida será-1.[2,3,2] <=> [2,2,2]Como arriba, primero comparará el primer elemento que sea igual a él, luego comparará el segundo elemento, en este caso, el segundo elemento de la matriz izquierda es mayor, por lo que la salida es
1.