I'm reading Comparable module.
And trying to see where Comparable module itself is implemented, but I can’t find it anywhere.
I only see places where it gets added using include.
Isn't that the module should have its implementation provided elsewhere? So that you just do a plug and play by using include?
Or is that in the following code:
class Geeksforgeeks
# include comparable module
include Comparable
attr :name
def <=>(other_name) # LineA
name.length <=> other_name.name.length # LineB
end
def initialize(name)
@name = name
end
end
LineA: is something at the Geeksforgeeks class level.
LineB: is something at Integer (Length) level.
If that's the case then where is <=> written for Integers?
EDIT:
My code builds without include Comparable. I'm just not so sure what it means though:
class Geeksforgeeks
# does not include Comparable
attr :name
def <=>(other_name) # LineA
name.length <=> other_name.name.length # LineB
end
def initialize(name)
@name = name
end
end
jack = Geeksforgeeks.new('jack')
pete = Geeksforgeeks.new('pete')
alexander = Geeksforgeeks.new('Alexander')
def areSameGeeks(g1, g2)
if g1 <=> g2
puts 'equal'
else
puts 'not equal'
end
end
areSameGeeks(jack,pete) # equal
areSameGeeks(jack, jack) # equal
areSameGeeks(jack, alexander) # equal
Like why are all three, returning 'equal'?
CodePudding user response:
And trying to see where
Comparablemodule itself is implemented, but I can’t find it anywhere.
Comparable is part of the core library of whatever Ruby implementation you are using. For example:
- in Rubinius,
Comparableis implemented incore/comparable.rb, - in TruffleRuby, it is implemented in
src/main/ruby/truffleruby/core/comparable.rb, - in MRuby, it is implemented in
mrblib/compar.rb, - in Opal, it is implemented in
opal/corelib/comparable.rb, - in JRuby, it is implemented in
core/src/main/java/org/jruby/RubyComparable.java, - in IronRuby, it is implemented in
Src/Libraries/Builtins/Comparable.cs, and - in YARV, it is implemented in
compar.c.
However, I personally find it not so much interesting where something is implemented but rather where it is specified. Comparable is specified in section 15.3.3 Comparable of the ISO/IEC 30170:2012 Information technology — Programming languages — Ruby specification. A less formal specification is given in core/comparable/ of The Ruby Spec Suite aka ruby/spec.
It is also described in The Ruby Programming Language by David Flanagan and Yukihiro 'matz' Matsumoto, Programming Ruby by Dave Thomas, Andy Hunt, and Chad Fowler, and of course in the Ruby documentation
If that's the case then where is
<=>written for Integers?
Integer#<=> is part of the core library of whatever Ruby implementation you are using. For example:
- in Rubinius,
Integer#<=>is implemented incore/integer.rb, - in TruffleRuby, it is implemented in
src/main/java/org/truffleruby/core/numeric/IntegerNodes.java, - in MRuby, it is implemented in
src/numeric.cwhich delegates tocmpnum, - in Opal, it technically does not exist (this is one of the few instances where Opal is not compliant with the Ruby Language Specification) because Opal does not have Ruby
Floats orIntegers, it only has ECMAScriptnumbers; for those,Number#<=>is implemented inopal/corelib/number.rb, - in JRuby,
Integeris an abstract class, so it only has a declaration ofInteger#<=>incore/src/main/java/org/jruby/RubyInteger.java, the actual implementations are in the two subclassesFixnum(core/src/main/java/org/jruby/RubyFixnum.java#L1043-L1060) andBignum(core/src/main/java/org/jruby/RubyBignum.java), - in IronRuby, it is implemented in
Src/Libraries/Extensions/ClrInteger.cs(at least forIntegers that fit into a C#int) and just delegates to C#'sint.CompareTo, and - in YARV, it is implemented in
numeric.cand delegates to eitherfix_cmporbig_cmp(defined inbignum.c).
However, I personally find it not so much interesting where something is implemented but rather where it is specified. Integer#<=> is specified in section 15.2.8.3.6 Integer#<=> of the ISO/IEC 30170:2012 Information technology — Programming languages — Ruby specification. A less formal specification is given in core/integer/comparison_spec.rb of The Ruby Spec Suite aka ruby/spec.
It is also described in The Ruby Programming Language by David Flanagan and Yukihiro 'matz' Matsumoto, Programming Ruby by Dave Thomas, Andy Hunt, and Chad Fowler, and of course in the Ruby documentation.
CodePudding user response:
<=> isn't implemented within the Comparable module:
https://ruby-doc.org/core-3.1.1/Comparable.html
This operation is implemented within each Ruby type (for example - String, Array, Integer). For default Ruby types it is possible to compare only objects of the same type, if you will try to compare it with something different you will get the nil value.
In your example LineA is a method for objects of Geeksforgeeks class, so you can use it as gfg_object <=> other_gfg_object. By the way your implementation of <=> isn't quite correct, it should checks that other_name is an instance of Geekforgeeks class (or another type) and return nil if it isn't. Correct example:
def <=>(object)
if object.is_a? Geekforgeeks
return name.length <=> object.name.length
elif object.is_a? String
return name.length <=>object.length
else
return nil
end
end
