[MacRuby-devel] Hash Table

Joshua Ballanco jballanc at gmail.com
Mon Apr 18 11:18:37 PDT 2011

Actually, it's quite a bit more complicated than that.

NSString, NSDictionary, and NSArray are class clusters. In practice, you are
never actually dealing with an "NSString", but rather a specialized subclass
in the class cluster. Originally, String in MacRuby was implemented using
NSCFString (one of NSString's cluster members) as a backing store, but
around 0.6 or 0.7 (my memory is foggy...Laurent and Vincent will know more)
Ruby's string implementation was changed so that now Ruby's string class is
completely custom, but it is a valid member of the NSString cluster (i.e. it
is a valid concrete subclass of NSString and NSMutableString). What does
this mean?

Well, the practical implication is that all Ruby Strings are valid
NSStrings, but not all NSStrings are valid Ruby strings. That is, if you are
interfacing with an Obj-C library that expects an NSString or NSMutable
string argument, you are safe to pass in any string created in Ruby.
However, if you are interfacing with an Obj-C library that returns an
NSString, you will need to turn this into a Ruby string before you do
Ruby-ish things too it. (If you're just turning around and pushing that
string back into an Obj-C library method that expects an NSString, you can
skip that step. Likewise, if you're only doing simple things like "puts"-ing
you can keep it as an NSString.)

Probably the most confusing thing about the situation as it currently
stands, is that MacRuby will insist that NSStrings are just "String"s, which
they aren't...quite... The issue is that if you need a string, sometimes an
NSString is sufficient and in those cases you'd want the NSString to report
itself as being the same as a String. In other cases, however, they are
different beasts. We'll probably have to come up with a better solution,
though, before the 1.0 release.

If you can make more sense of code than of words, here it is in code:


irb(main):001:0> ns = NSString.stringWithString('Test')
=> "Test"
irb(main):002:0> ns.class
=> String
irb(main):003:0> ns.class.ancestors
=> [String, NSMutableString, NSString, Comparable, NSObject, Kernel]
irb(main):004:0> puts ns
=> nil
irb(main):005:0> ns.gsub!(/T/, 't')
RuntimeError: can't modify frozen/immutable string

irb(main):006:0> rb = String.new(ns)
=> "Test"
irb(main):007:0> rb.class
=> String
irb(main):008:0> rb.class.ancestors
=> [String, NSMutableString, NSString, Comparable, NSObject, Kernel]
irb(main):009:0> puts rb
=> nil
irb(main):010:0> rb.gsub!(/T/, 't')
=> "test"




On Mon, Apr 18, 2011 at 1:40 PM, Joe West <mrjoewest+macruby-devel at gmail.com
> wrote:

> On Mon, Apr 18, 2011 at 10:40 AM, Ricky Chilcott
> <ricky at rickychilcott.com> wrote:
> >
> > I'd noticed that too. I thought Strings were actually NSStrings.
> >
> They are NSMutableStrings/NSStrings underneath:
> irb(main):013:0> "string".class.ancestors
> => [String, NSMutableString, NSString, Comparable, NSObject,
> PP::ObjectMixin, Kernel]
> And hashes are similarly NSMutableDictionary/NSDictionary:
> irb(main):015:0> {}.class.ancestors
> => [Hash, NSMutableDictionary, NSDictionary, Enumerable, NSObject,
> PP::ObjectMixin, Kernel]
> Couldn't say for sure, but seems like a good move to improve
> consistency/compatibility with non-MacRuby code and gems and the like.
> Joe
> _______________________________________________
> MacRuby-devel mailing list
> MacRuby-devel at lists.macosforge.org
> http://lists.macosforge.org/mailman/listinfo.cgi/macruby-devel
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.macosforge.org/pipermail/macruby-devel/attachments/20110418/9b81452b/attachment.html>

More information about the MacRuby-devel mailing list