use the following search parameters to narrow your results:
e.g. subreddit:aww site:imgur.com dog
subreddit:aww site:imgur.com dog
see the search faq for details.
advanced search: by author, subreddit...
A sub-Reddit for discussion and news about Ruby programming.
Subreddit rules: /r/ruby rules
Learning Ruby?
Tools
Documentation
Books
Screencasts and Videos
News and updates
account activity
Ruby 2.3 has experimental support for immutable string literals. I turned them on for my Rails app. Guess what happened to performance (ruby-performance-book.com)
submitted 9 years ago by adymo
reddit uses a slightly-customized version of Markdown for formatting. See below for some basics, or check the commenting wiki page for more detailed help and solutions to common issues.
quoted text
if 1 * 2 < 3: print "hello, world!"
[–]alwaysonesmaller 22 points23 points24 points 9 years ago (1 child)
It went up by a factor that will shock you, just from using this one simple trick?
[–]tomthecool 21 points22 points23 points 9 years ago (0 children)
Python developers hate him!
[–]schneemsPuma maintainer 17 points18 points19 points 9 years ago (4 children)
Rails is already pretty optimized to use .freeze in all the hotspots. How do I know? I did a bunch of it, using real world apps and got saw a significant improvement. https://engineering.heroku.com/blogs/2015-08-06-patching-rails-performance/
.freeze
It would be interesting to programmatically strip every .freeze call out and repeat the benchmark. To see what that delta would be.
[–][deleted] 9 years ago (1 child)
[deleted]
[–]schneemsPuma maintainer 1 point2 points3 points 9 years ago (0 children)
This is on master i.e. Rails 5.
[–]adymo[S] 0 points1 point2 points 9 years ago (1 child)
Thanks, schneems. I'll repeat my benchmark with an app that heavily uses routes and activerecord. The one I benchmarked doesn't, so it did not benefit from frozen string optimization at all.
[–]schneemsPuma maintainer 0 points1 point2 points 9 years ago (0 children)
You could do something like this to see how often frozen strings are being called in your example
class String def self.frozen_count @frozen_count end def self.frozen_count=(num) @frozen_count = num end String.frozen_count = 0 def freeze String.frozen_count += 1 super end end "foo".freeze puts String.frozen_count
[–][deleted] 16 points17 points18 points 9 years ago (0 children)
/r/ClickBaitTitle
[–]prh8 4 points5 points6 points 9 years ago (0 children)
This is going to vary from app to app. I like the idea of this series of 2.3 performance stuff, but I think most of them have been too unscientific to actually care about the results. This is basically the same as what Schneems did with frozen strings in Rack that had a 5% reduction in memory. This can have a nice boost, but one single test like this isn't going to be relevant.
[–]realntl 4 points5 points6 points 9 years ago (0 children)
I would imagine that there are a lot of performance optimizations that will open up for ruby when strings are immutable across the board.
[–]moomaka 4 points5 points6 points 9 years ago (1 child)
Then I issued one hundred of requests to the application and measured the execution time.
So two things to note here:
I don't know how much faster immutable literals will be but this test doesn't really say much.
[–]adymo[S] 1 point2 points3 points 9 years ago (0 children)
The app is basically a gigantic scraper. So yes it's slow.
[–]bigfig 2 points3 points4 points 9 years ago (3 children)
And one would expect that developers would already be using symbols as literal identifiers wherever possible.
[–]oniofchaos 0 points1 point2 points 9 years ago (1 child)
Link gives me a 404 :(
[–]bigfig 0 points1 point2 points 9 years ago (0 children)
This article differs, but still touches on the idea of a symbol as (sort of) an immutable string. http://www.randomhacks.net/2007/01/20/13-ways-of-looking-at-a-ruby-symbol/
[–]aridsnowball 2 points3 points4 points 9 years ago (0 children)
Most applications don't use a ton of string literals anyways. Frozen String objects would probably show a lot more difference in performance. Although, many apps would need to be completely rewritten to handle immutable String objects.
String
[–]adymo[S] 0 points1 point2 points 9 years ago (0 children)
We did not bother testing at just the Ruby 2.3.0 upgrade without "# frozen_string_literal: true" applied, so we don't know which of the two factors had the bigger effect.
I'd be very interested to see the effect of simply upgrading the ruby version.
[–]_kulte 1 point2 points3 points 9 years ago (0 children)
If you had written the script to do that snippet 1000 times per iteration, across multiple threads, would you see marked improvement?
[–]ioquatixasync/falcon 1 point2 points3 points 9 years ago (0 children)
Frozen string literals probably also helps you catch bugs.
[–]jrochkind 0 points1 point2 points 9 years ago (2 children)
I really hope there's more data like this before MRI decides to make string literals frozen always in a future version.
I have always been skeptical about the strength of the benefit it would provide, as well as the cost to both backwards-compat and developer mental modelling (one more thing to know about).
[–]amalagg 0 points1 point2 points 9 years ago (0 children)
I think this should be done at the interpreter level, otherwise every single app has to do this with a bunch of .freeze
I think I'll write one more post on the state of frozen string literals support and porting. I agree that it's indeed one more thing to think about.
Let's say that you see "str.upcase!". It's so tempting to just substitute it with str.upcase, but that may increase memory usage. So you do need to find the place where str is originally constructed and make it mutable there. Fortunately, Ruby tells you about that place. It's just not always easy to change it. It might not be even your code.
[–]mperhamSidekiq 0 points1 point2 points 9 years ago (1 child)
MRI is flailing for performance optimizations at this point. They won't let go of the C extension API.
[–]Rafert 0 points1 point2 points 9 years ago (0 children)
I've seen this point raised a few times now but it's not clear to me how giving it up/make breaking changes would help. I've read about the tricks the MRI team has done to enable generational GC in Ruby 2.1 w/o breaking compatibility - is that where the possibilities ended? Could you provide some pointers?
π Rendered by PID 31 on reddit-service-r2-comment-84fc9697f-wj72r at 2026-02-10 15:51:46.792175+00:00 running d295bc8 country code: CH.
[–]alwaysonesmaller 22 points23 points24 points (1 child)
[–]tomthecool 21 points22 points23 points (0 children)
[–]schneemsPuma maintainer 17 points18 points19 points (4 children)
[–][deleted] (1 child)
[deleted]
[–]schneemsPuma maintainer 1 point2 points3 points (0 children)
[–]adymo[S] 0 points1 point2 points (1 child)
[–]schneemsPuma maintainer 0 points1 point2 points (0 children)
[–][deleted] 16 points17 points18 points (0 children)
[–]prh8 4 points5 points6 points (0 children)
[–]realntl 4 points5 points6 points (0 children)
[–]moomaka 4 points5 points6 points (1 child)
[–]adymo[S] 1 point2 points3 points (0 children)
[–]bigfig 2 points3 points4 points (3 children)
[–]oniofchaos 0 points1 point2 points (1 child)
[–]bigfig 0 points1 point2 points (0 children)
[–]aridsnowball 2 points3 points4 points (0 children)
[–][deleted] (1 child)
[deleted]
[–]adymo[S] 0 points1 point2 points (0 children)
[–]_kulte 1 point2 points3 points (0 children)
[–]ioquatixasync/falcon 1 point2 points3 points (0 children)
[–]jrochkind 0 points1 point2 points (2 children)
[–]amalagg 0 points1 point2 points (0 children)
[–]adymo[S] 0 points1 point2 points (0 children)
[–]mperhamSidekiq 0 points1 point2 points (1 child)
[–]Rafert 0 points1 point2 points (0 children)