String::Builder
Refinement of the core String class, extending it with class and instance methods for streamlined string construction.
Methods
There are four new methods in this extension of the String
class:
Instance methods
String#build
Takes a block yielding a new builder string, and appends the builder string to a duplicate of the original String
object, self
.
Examples
= 'foo'.build do |s|
s << 'bop'
s.gsub!('op','ar')
end
#=> "foobar"
foo = 'foo'
= foo.build do |s|
s << 'bop'
s.gsub!('op','ar')
end
#=> "foobar"
String#build!
Takes a block yielding a new builder string, and appends the builder string to the original String
object, self
.
NOTE: This mutates the original string, as indicated by the bang !
.
Example
= 'foo'
.build! do |s|
s << 'bop'
s.gsub!('op','ar')
end
#=> "foobar"
Class methods
String.build
Takes an arbitrary object and a block yielding a new string builder, and appends the builder string to a duplicate of the object parameter converted to a string (with to_s
).
If no block is given, then the object converted to a string (with to_s
) is returned.
Examples
= String.build do |s|
s << 'fii'
s.gsub!('ii','oo')
s << 'bar'
end
#=> "foobar"
= String.build 'foo' do |s|
s << 'bop'
s.gsub!('op','ar')
end
#=> "foobar"
= String.build 3 do |s|
s << 'bop'
s.gsub!('op','ar')
end
#=> "3bar"
foo = 'foo'
= String.build foo do |s|
s << 'bop'
s.gsub!('op','ar')
end
#=> "foobar"
foo #=> "foo"
String.[]
Takes arbitrarily many objects (with splat), converts them to strings and contatenates them (takes the product with the empty string).
Examples
String[] #=> ""
String[3] #=> "3"
String['Hello','World','!'] #=> "HelloWorld!"
String[{k: 'v'}, 3, %i[a b c]] #=> "{:k=>\"v\"}3[:a, :b, :c]"
String[*['a', 2, :z]] #=> "a2z"
Detailed example
This example shows how to make a simple logger by constructing log messages with String::Builder
.
Suppose we want a Logger
class that allows us to do the following:
logger = Logger.new
logger.error 'String::Builder is good?'
#=> [03:54:53s] (lib/string-builder.rb) ERROR » String::Builder is good!
logger.success 'String::Builder is good?'
#=> [03:54:55s] (lib/string-builder.rb) SUCCESS » String::Builder is good!
logger.info 'String::Builder is good?'
#=> [03:54:57s] (lib/string-builder.rb) INFO » String::Builder is good!
logger.warning 'String::Builder is good?'
#=> [03:54:59s] (lib/string-builder.rb) WARNING » String::Builder is good!
Class method - String.build
require 'string/builder'
class Logger
using String::Builder
%i[error success info warning].each do |severity|
define_method(severity) do ||
time = Time.now.strftime("[%H:%M:%Ss]")
String.build time do |s|
s << " (#{__FILE__})"
s << " #{severity.to_s.upcase} » #{}"
s.gsub!('?','!')
end
end
end
end
Instance method - String#build
The class shown above can use the String#build
instance method to achieve the same functionality.
require 'string/builder'
class Logger
using String::Builder
%i[error success info warning].each do |severity|
define_method(severity) do ||
time = Time.now.strftime("[%H:%M:%Ss]")
time.build do |s|
s << " (#{__FILE__})"
s << " #{severity.to_s.upcase} » #{}"
s.gsub!('?','!')
end
end
end
end
Installation
Add this line to your application's Gemfile:
gem 'string-builder'
And then execute:
$ bundle
Or install it yourself as:
$ gem install string-builder
Usage
This extension is in the form of a refinement
. This means that you will have to call the following using
directive within the scope that you want the String
class to be extended with String::Builder
methods:
require 'string/builder'
using String::Builder
Though you should typically avoid doing this in the global scope (unless you really need to), and instead only use the extension where you need it - inside your specific modules or classes:
require 'string/builder'
class A
using String::Builder
# CAN use String::Builder methods in this class
end
module B
# CANNOT use String::Builder methods in this module
end
# CANNOT use String::Builder methods in the global scope
Further information
For more information about string-building in Ruby and Crystal, read this blog post.