or '''P''''''ettyLittleRubyComplaints''' ...just following the W''''''hyWeHate pattern. ''Nobody ''really'' hates RubyLanguage...right?'' ...but only a close relationship exits as this reaction indicated. * Perlisms ** Why does Ruby include some sugar to make your beautiful Ruby code look half Perl? Does Matz actually use these things or does he use the more ''pure'' Ruby alternatives? Is it to attract PerlLanguage programmers? Does this work? Was Ruby more accessible to ''me'' because of this? *** ''Because a prime Ruby directive is "easiest for the programmer". Adopting ONLY "if str ~= /foo (bar)/ then $1" from Perl avoids crud like Python's horrific re.search() method, which you can't even put into an if!'' **** Sure you can- re.search returns a True value (MatchObject) on a match, and a False value (None) on no match. Unless you mean you want store the match, too, in which case that doesn't belong in an if condition anyway **Parentheses are usually not necessary around method arguments. But sometimes they are. Just like Perl. Arg. ** See ThereIsMoreThanOneWayToDoIt below. ** Sometimes you ''must'' use the Perlisms. For example, there's no String#endswith method. So, instead of foo.endswith('bar'), you must use Perl syntax RegularExpression matching: foo =~ /bar$/ *** This is no longer true. String class has an ends_with? method as of 1.9. *** Why not: %r{bar$}.match(foo)? Or if that's still too Perlish for you: Regexp.new('bar$').match(foo)? Plus, Ruby allows you to add an endswith() method to String to wrap that if you want. *** You expect me to do all that typing when foo =~ /bar$/ is much simpler? :-) Okay, okay, so I don't have to use the RegExp Perlism. But ''not'' using it is too much work. *** There is an end_with? method; see http://www.ruby-doc.org/core/classes/String.html#M001180 *Semi-significant whitespace ** Actually, this doesn't bother ''me'', but I'm including it on the assumption that it bothers someone. (^_^) ** While not whitespace, the case-significant variables are annoying. *It's not SmalltalkLanguage, though it tries really hard to be. ** Control constructs that aren't implemented with blocks ** Verbose syntax for blocks that aren't the last parameter to a function *** A brief block syntax is good. If you have one, you should use it for ''all'' blocks. ** See also RubyIsSmalltalkMinusMinus. * ThereIsMoreThanOneWayToDoIt ** Interfaces in the Core API are bloated: Array.map == Array.collect, Enumerable.detect == Enumerable.find, Enumerable.find_all == Enumerable.select, Enumerable.to_a == Enumerable.entries, Hash.has_key? == Hash.include? == Hash.key? == Hash.member?, Hash.has_value? == Hash.value?, Hash.indexes == Hash.indices, Hash.length == Hash.size, Hash.merge! == Hash.update, String.succ == String.next, etc. ** No fewer than four ways to define class-scoped methods ** Blocks can be surrounded with braces. Or whitespace. Or keywords. * Doesn't respect PrincipleOfLeastSurprise ** The object_id value for integers is the integer multiplied by two, plus one. * Idiomatic use of the '_' character for word separation (SnakeCase EmbeddedUnderscore); it's just damn ugly. ** Aside from it being damn ugly, it's also harder to type a shifted symbol on the top row when your fingers are on the home row typing lowercase letters. * No TailCallOptimization. ** You can turn this on in MRI Ruby 1.9, 2.0 and 2.1 ** Also, Ruby's stack depth is exceeded far sooner than Python's. *** Which is impressive. * "Documentation" is scattered all over the internet. ** I have to refer to Zen Spider's Ruby Quick''''''Ref to find the built-in Exception hierarchy, the online PickAxeBook to read how to open a file, the RubyGarden wiki to learn about RubyCoerce, etc., etc., etc. * Core and Standard API docs are incomplete, misleading, or wrong. ** The File class "is closely associated with class IO," yet the docs fail to say that File is a ''subclass'' of IO. ** Most Set methods return fresh Sets, yet the docs claim they return Arrays. * RDoc-generated documentation sucks ** The gray backgrounds are too dark. Spotting a method name against medium gray is difficult. ** Each unit in the Standard Library has its own CascadingStyleSheets file, making it nigh unto impossible to change style across the board, especially if you want to update your library. * What's with the PragmaticProgrammer publisher appearing overnight and monopolizing the publication of Ruby books? ** I call BS. Pragmatic published a couple first, because 1) no one else wanted to at that time, and 2) they have a very short pipeline. "Monopolizing" would have been if they'd prevented other people from doing the same, which they haven't. They were just "first with the most". ** ''The main bullet point should be read with an IronyWarning.'' * Can't right associate operators ** Suppose you define a Vector class and you define its '*' operator for 'vector * number'. That's fine, but good luck defining the same for 'number * vector'. Good luck making your multiplication commutative. ** You can do this, it is called RubyCoerce and there are links there which explain it. I have used it to enable addition of numbers to user defined objects, including interfaced code written in CeePlusPlus. -- JohnFletcher ** Yup. But the rdocs are not helpful, and this is not in the online Pickaxe. As usual, Ruby documentation is exasperating and how to do this in PythonLanguage is so much more obvious. Plus, there's more to this saga... -- ElizabethWiethoff * The Ruby community has a big problem with NIH (NotInventedHere) and a superiority complex. ** Rather than use common method names from other runtimes, it goes out of it's way to pick new and less intuitive names *** e.g. String.toLowerCase() becomes String.downcase() **** "downcase" is pretty common in my world. * Horrible suffix characters that you thought you'd got rid of when you ditched BASIC ** And some of them make for methods that differ based only on the suffix *** e.g. String.chop vs String.chop! - where the latter does damage to the instance because Ruby has MutableStrings * MutableStrings ** Seriously. Ick. * The implementation is ugly and buggy. I've found two significant bugs; one of which is arguably a security hole. * SmugRubyWeenie''''''s * RubyOnRailsRulesTheUniverse ''(oy!)'' * DomainSpecificLanguage fever: look.ma no.parentheses! excited.weenies.every do |weenie| weenie.invents_a.domain_specific.language end ''.nuff.said . ** But they still haven't got rid of the pipes. If they really wanted Englishification: look.ma no.parentheses.and.no.pipes! excited.weenies.every do with weenie weenie.invents_a.domain_specific.language end // examples damaged by TabMunging . ** Is it just me, or does using such DSL features of those lisp-wannabe language make for cryptic error messages versus a "real" DSL (custom compiler/interpreter)? The round-about innards of implementation seem to expose themselves when something goes wrong. Same with JavaScript. I don't currently have any such examples to present, but will keep an eye for them. -t * The only common superclass of True and False is Object. * you don't get a stacktrace when you hit a SystemStackError; how useful! You need to fall back to ugly and inconvenient trickery like: http://stackoverflow.com/a/21585967/520567 -------- Lisp, SmallTalk, JavaScript, and Perl walked into a bar and had an orgy near Fukishima, giving birth to a 30-pound bi-gender baby named Ruby. ---- If Ruby docs frustrate the daylights out of you, as they do me, you might find my Ruby API Guide (http://mysite.verizon.net/hpassel/rubyguide/) helpful. Even though it has a ways to go, I find myself referring to it all the time. It's helping me a ''lot''. -- ElizabethWiethoff [DeadLink?] ------ It suffer some of the pitfalls of Lisp, as described in GreatLispWar. ---- CategoryRant CategoryRuby