<\/span>class<\/span> <\/span>Chars<\/span>
<\/span> <\/span>
<\/span> <\/span>attr_reader<\/span> <\/span>:string<\/span> <\/span># The contained string<\/span>
<\/span> <\/span>alias_method<\/span> <\/span>:to_s<\/span>,<\/span> <\/span>:string<\/span>
<\/span> <\/span>
<\/span> <\/span>include<\/span> <\/span>Comparable<\/span>
<\/span> <\/span>
<\/span> <\/span># The magic method to make String and Chars comparable<\/span>
<\/span> <\/span>def<\/span> <\/span>to_str<\/span>
<\/span> <\/span># Using any other ways of overriding the String itself will lead you all the way from infinite loops to<\/span>
<\/span> <\/span># core dumps. Don\'t go there.<\/span>
<\/span> <\/span>@string<\/span>
<\/span> <\/span>end<\/span>
<\/span> <\/span>
<\/span> <\/span># Make duck-typing with String possible<\/span>
<\/span> <\/span>def<\/span> <\/span>respond_to?<\/span>(<\/span>method<\/span>)<\/span>
<\/span> <\/span>super<\/span> <\/span>||<\/span> <\/span>@string<\/span>.<\/span>respond_to?<\/span>(<\/span>method<\/span>)<\/span> <\/span>||<\/span> <\/span>handler<\/span>.<\/span>respond_to?<\/span>(<\/span>method<\/span>)<\/span> <\/span>||<\/span>
<\/span> <\/span>(<\/span>method<\/span>.<\/span>to_s<\/span> <\/span>=<\/span>~<\/span> <\/span>/<\/span>(.*)!<\/span>/<\/span><\/span> <\/span>&&<\/span> <\/span>handler<\/span>.<\/span>respond_to?<\/span>(<\/span>$1<\/span>)<\/span>)<\/span> <\/span>||<\/span> <\/span>false<\/span>
<\/span> <\/span>end<\/span>
<\/span> <\/span>
<\/span> <\/span># Create a new Chars instance.<\/span>
<\/span> <\/span>def<\/span> <\/span>initialize<\/span>(<\/span>str<\/span>)<\/span>
<\/span> <\/span>@string<\/span> <\/span>=<\/span> <\/span>str<\/span>.<\/span>respond_to?<\/span>(<\/span>:string<\/span>)<\/span> <\/span>?<\/span> <\/span>str<\/span>.<\/span>string<\/span> <\/span>:<\/span> <\/span>str<\/span>
<\/span> <\/span>end<\/span>
<\/span> <\/span>
<\/span> <\/span># Returns -1, 0 or +1 depending on whether the Chars object is to be sorted before, equal or after the<\/span>
<\/span> <\/span># object on the right side of the operation. It accepts any object that implements +to_s+. See String.<=><\/span>
<\/span> <\/span># for more details.<\/span>
<\/span> <\/span>def<\/span> <\/span><=><\/span>(<\/span>other<\/span>)<\/span>;<\/span> <\/span>@string<\/span> <\/span><=><\/span> <\/span>other<\/span>.<\/span>to_s<\/span>;<\/span> <\/span>end<\/span>
<\/span> <\/span>
<\/span> <\/span># Works just like String#split, with the exception that the items in the resulting list are Chars<\/span>
<\/span> <\/span># instances instead of String. This makes chaining methods easier.<\/span>
<\/span> <\/span>def<\/span> <\/span>split<\/span>(<\/span>*<\/span>args<\/span>)<\/span>
<\/span> <\/span>@string<\/span>.<\/span>split<\/span>(<\/span>*<\/span>args<\/span>)<\/span>.<\/span>map<\/span> <\/span>{<\/span> <\/span>|<\/span>i<\/span>|<\/span> <\/span>i<\/span>.<\/span>chars<\/span> <\/span>}<\/span>
<\/span> <\/span>end<\/span>