
Ruby 2.4.0 Released - sply
https://www.ruby-lang.org/en/news/2016/12/25/ruby-2-4-0-released/
======
ksec
Compared to Rust, Go. The list of improvement for a yearly Ruby version is
rather small. Some will argue Rust and Go are relatively new, but there are
actually LOTS of low level performance improvement done within a year time
frame.

Even if you compared to Python 3, the improvement is still rather small.

I know there is always the argument about the lack of resources, and Rust is
being backed by Mozilla while Go is being backed by Google. But what about
Python?

Exactly how much money is Mozilla spending on Rust, paying how many developers
full time? Apple JS Core team is incredibly small, but they manage a B3 JIT
compiler with 2 people.

How much money is needed? Matz and Tenderlove both mention they need more
resources. Surely we can fund rise? With lots of successful companies using
Ruby on Rails. Basecamp, Twitter, Groupon, Github, Gitlab etc. Or Ruby
communities lack the compiler / JIT expert, can we hired some?

I am not trying to downplay the Ruby improvement. But I think Ruby needs more
contributors. Moving to GitHub to get a higher exposure has been banned due to
GitHub not being an opensoure product. But they also dislike hosting on Gitlab
for some strange reason.

~~~
jonnytran
What do you mean moving to GitHub has been banned? This isn't it?
[https://github.com/ruby/ruby](https://github.com/ruby/ruby)

~~~
halostatue
There are core contributors who would no longer participate because they
refuse to use proprietary systems, even remote ones, and do not even run
JavaScript. Matz prefers overall inclusivity to losing the contributors, so a
wholesale move to GitHub (instead of RubyMine) is not going to happen.

------
sply
Performance related:

    
    
      * Hash improvements via better locality for modern CPUs
      * #max and #min without temporary array
      * Speed up instance variable access

~~~
nateberkopec
Regexes also had some changes which have improved our results on regex-heavy
benchmarks by as much as 3x.

~~~
dvdhnt
Nice! That's good to know.

------
dollar
I still love you, Ruby. I wish we spent more time together.

~~~
hota_mazi
I was madly in love with Ruby in 2005 but now, Ruby feels like this ex
girlfriend you were completely infatuated with and eventually broke up with
because you were too young to pay attention to her flaws.

~~~
nstart
Since I never picked up ruby (I joined Python and now I'm about to pick up
ruby). Curious what made you move away and what you've moved to?

~~~
hota_mazi
It's dynamically typed, which is a deal breaker for me today. I need not just
a type system but one that supports parametric polymorphism, so definitely not
Ruby, Python or even Go.

~~~
xapata
You can use traits instead. I know it's different, but it probably solves your
problem.

~~~
hota_mazi
Traits are orthogonal to the dynamic/static question.

My experience has taught me that not having type annotations in a source code
makes it very hard to understand and maintain that source in the long run.

~~~
vidarh
Ruby is more than flexible enough for you to add type annotation via DSLs, and
use them to drive tests/fuzzing if you want that. There are a lot of people
who have done that.

They rarely see much use, though, because most of us quickly experience that
the type annotations that _seem_ essential when we work on statically typed
languages quickly become less essential once you adopt a more idiomatic Ruby
style.

E.g. if you want to output something as text, rather than dictate what should
be passed in, call #to_s on it (and optionally handle the failure if it
doesn't implement #to_s, if it is reasonable to continue).

Once you adopt the attitude of asking for what you actualy _need_ rather than
demanding the client pass in what _you_ think should be passed in, type
annotations start feeling like a clamp around your foot rather than a
necessity in most cases, and most of the remaining assistance they could
provide tends to fall away with test cases you would require in either case.

I used to be a static typing zealot, and I still want things to be "as static
as possible", but I've come to accept that most of the time the burdens it
adds are not worth the benefits.

I'm sure we can do better, and there are certainly cases where optional static
type annotation could be helpful, but at this point I'm not giving up the
expressiveness dynamc typing gives me - a static system would need to be
practically "invisible" for me to find it acceptable.

------
alxjrvs
Pretty cool to see a binding.pry analog moved into the standard library.

~~~
gkop
Could binding.pry/binding.irb be shortened at all? It's a mouthful.

~~~
fidz
Sure.

    
    
        require 'pry'
        module Kernel
          def debug; binding.pry; end
        end
        
        x = "hi"
        debug

~~~
lparry
Won't the binding then be your monkey patched debug method on kernel instead
of where you called it from?

~~~
sirn
Yes.

    
    
        irb(main):008:0> x = "1"
        => "1"
        irb(main):009:0> debug
        [1] pry(main)> x
        NameError: undefined local variable or method `x' for main:Object
        from (pry):1:in `debug'
    

If you really want to do this, you can use binding_of_caller[1] to create
binding object (`Kernel.binding`) up in the call stack:

    
    
        require 'binding_of_caller'
        require 'pry'
        
        module Kernel
          def debug
            binding.of_caller(1).pry
          end
        end
    

Then:

    
    
        irb(main):008:0> x = "1"
        => "1"
        irb(main):009:0> debug
        [1] pry(main)> x
        => "1"
    

[1]:
[https://github.com/banister/binding_of_caller](https://github.com/banister/binding_of_caller)

------
woodruffw
Interesting choice to remove `tk` from the stdlib. It always felt a little
neglected in terms of documentation and maintenance, but it was nice to have a
simple graphical toolkit guaranteed with the runtime.

~~~
vinceguidry
I tried to use it, settled on Shoes instead. Tk isn't free, you still have to
install OS dependencies, and it's API wasn't very Rubyish.

You'd think Ruby would be swimming in easy-to-use widget libraries. But it
still isn't. Shoes fits most of my needs, though I'm still working on my
workflows and tooling. It's annoying that I can't just write to the console or
drop in a pry session, but I'm slowly figuring it out.

~~~
woodruffw
Yeah, Tk certainly isn't a _pleasure_ to work with in Ruby. Maybe my
experience was colored by the fact that it always worked out-of-the-box on my
desktop (I guess the libraries were preinstalled).

I've looked at Shoes multiple times for various projects and it always looks
_terrific_ , until I remember that installing it involves downloading a 64-bit
binary from a website. I've bitten the bullet before and done it, but it's an
(ugly) step backwards compared to `gem` and the Qt/Gtk+ bindings that can be
installed via `gem`.

~~~
steveklabnik
Yeah, shoes :( Such potential. I could never quite get it updated to Ruby 1.9.
Sigh.

------
nikic
It looks like recently, there has been a convergence of hashtable
implementations across a number of programming languages. Details differ, but
the general structure is now to use two arrays, one for storing the data in
insertion order (thus maintaining order without a doubly linked list), and
another array serving as a hash, which contains indexes into the data array.
This general idea works both with chaining and open addressing. In the last
couple of years PHP (first HHVM then Zend), then Python (first PyPy then
CPython), then Ruby (MRI) have switched to using this layout. Interestingly,
Python has previously not made guarantees about order of hashtable elements,
so this layout is advantageous even if maintaining insertion order is not a
hard design constraint.

~~~
euyyn
How do they remove elements from the first array? Suck it and do O(N), or is
it storing (value, deleted?) pairs?

~~~
brianwawok
Look at the index as given by the hash?

~~~
euyyn
Oh, so as you iterate the array, look up the value in the hash and if it's not
there skip it?

The downside is you end up accumulating dead values.

------
vortico
Why was BigInt and FixNum unified into Integer? Don't they already both
subclass Integer?

It seems they just made it harder to write interfaces that take advantage of
machine precision integers. They didn't remove either arbitrary precision
integers or machine precision integers, they just made them harder to
distinguish. Why is this an improvement?

~~~
riffraff
because the existence of Bignum and Fixnum is effectively an implementation
detail, Float is now implemented in a similar way for example, without having
corresponding Flonum and Bigfloat.

There isn't (at least I've never seen it) any reason to distinguish between
the two, Fixnum wasn't the proper tool to do machine-precision integer
operations either (31 bit).

~~~
vortico
But isn't hiding implementation details best done by using an interface (like
the Integer superclass) rather than some flag somewhere with branching logic?
Fixnum _is_ useful for C extensions to quickly convert to `int`, but now I
suppose you don't know whether an Integer is cast-able to an `int` unless you
inspect this flag in a new custom way.

------
taf2
Looks like it breaks gem install json -v '1.8.3' \- it does however work with
json 2.0.2

------
wasd
And it's likely the static vs dynamic programming debate has been around
longer than you coding ;).

~~~
dang
We detached this subthread from
[https://news.ycombinator.com/item?id=13252935](https://news.ycombinator.com/item?id=13252935)
and marked it off-topic.

------
nodesocket
Not sure why they decided to release on Christmas eve / day, but looks good.

~~~
raitom
Because tradition. Most of the major ruby version are released on christmas
day.

~~~
rurban
And it actually comes from perl, which used to announce their next big release
on christmas. but it never came, and they claimed they never said which
christmas, just one eventually.

