Strings in Ruby
Tags: ruby, programming, codenewbie, beginners
Published: 2022-06-10 02:11:18

**_Quick index_**
1. [String Creation](#string-creation)
2. [Single and Double quotes](#single-hard-and-double-soft-quotes)
3. [String Manipulation](#string-manipulation )
  1. [Escape Characters](#escape-characters)
  2. [Concatenation](#concatenation)
  3. [Substrings](#substrings)
  4. [Methods](#methods)
4. [Symbols vs Strings](#symbols-vs-strings)
5. [References](#references)


##String creation 
+ A string can be created by using String literal: 
```ruby 
greetings = 'hello all!'
```

+ with [`String::new`](https://ruby-doc.org/core-3.1.2/String.html#method-c-new) you have more options for creating a string, mostly regarding the encoding type you want your string:
```ruby 
greetings = String.new('hello all!', encoding: 'ASCII')
```

+ or if you need a multiline string, you can use [`heredoc literal`] (https://ruby-doc.org/core-3.1.2/doc/syntax/literals_rdoc.html#label-Here+Document+Literals): 
```ruby
s = <<HEREDOC
This would contain specially formatted text.

That might span many lines
HEREDOC
```
Note that it is a good way to add snippets of code, specially SQL if you are in the backend connected to the database, for example. 
 
It preserves the original formatting and can have interpolation inside of it as well. Here we have two good examples from [Ruby Guides](https://www.rubyguides.com/2018/11/ruby-heredoc/): 

```ruby 
type  = "healthy"
table = "food"
query = <<-SQL
SELECT * FROM #{table}
WHERE #{type} = true
SQL
```

```ruby 
doc = <<-TIME
Current time is #{Time.now}
TIME

print doc  #=> Current time is 2022-06-07 14:51:09 +0000
```

We can use single quotes to disable the interpolation.

```ruby
doc = <<-'TIME'
Current time is #{Time.now}
TIME

print doc  #=> Current time is #{Time.now}
```

##Single (hard) and double (soft) quotes

> **Interpolation**: `#{` sequence `}`. We can place any code inside it. It is very useful.  

+ We call single quotes as _hard quotes_ because it is **_not_** possible to use interpolation within it, nor escape characters. 

```ruby
name = 'all'
print 'hello #{name}!'  #=> hello #{name}!
```
+ On the other hand, double quotes allows interpolation and to escape chars, and that is why we call it _soft quotes_. 

```ruby
name = 'all'
print "hello #{name}!"  #=> hello all!
```

⁉️ For readability, it is recommended to use doble quotes only when the interpolation is present, but there is no problem if you decide to use only double quotes through your code. 

## String Manipulation 
### Escape Characters
Some chars have a special meaning. For example, `"` can terminate a string before the intended. We can add a backslash in front of it to be able to display it in our string.

```ruby 
print "Double quotes: \""  #=> Double quotes: "
```

Here is a list of some escape sequences:

|escape sequences      |                       |
|----------------------|----------------------:|
|\b                    |backspace, ASCII 08h (BS)|
|\t                    |horizontal tab, ASCII 09h (TAB)|
|\n                    |newline (line feed), ASCII 0Ah (LF)|
|\v                    |vertical tab, ASCII 0Bh (VT)|
|\f                    |form feed, ASCII 0Ch (FF)|
|\r                    |carriage return, ASCII 0Dh (CR)|
|\e                    |escape, ASCII 1Bh (ESC)|
|\s                    |space, ASCII 20h (SPC)|
|\\                    |backslash, \|
|\nnn                  |octal bit pattern, where nnn is 1-3 octal digits ([0-7])|
|\xnn                  |hexadecimal bit pattern, where nn is 1-2 hexadecimal digits ([0-9a-fA-F])|
|\unnnn                |Unicode character, where nnnn is exactly 4 hexadecimal digits ([0-9a-fA-F])|


### Concatenation 
The same way you can use interpolation to group strings, you can use concatenation. 

```ruby 
print 'hello' + ' all' #=> hello all
```
```ruby
print 'hello' << ' all' #=> hello all
```
```ruby
print 'hello'.concat(' all') #=> hello all
```

### Substrings
We can access substrings by accessing its indexes just like we would do with an array. 

```ruby 
"hello"[0]      #=> "h"

"hello"[0..1]   #=> "he"

"hello"[0, 4]   #=> "hell"

"hello"[-1]     #=> "o"
```

### Methods
There is a long list of methods to support you to handle a string. What is important to note is that _in general_ methods ending with a bang mutantes `self` and returns `self`.

Methods that do not have a bang, _usually_, do not mutate and return a new string.

take the methods `capitalize` and `capitalize!` as an example: 

```ruby 
a = "hello all!"
a.capitalize

print a #=> hello all!

a.capitalize!

print a #=> Hello all!
```

Best practice is always to pay attention to the return. Some methods like `replace` does not have a bang, but modifies `self` either way. 

You can take a look at the methods available [here](https://ruby-doc.org/core-3.1.2/String.html)

## Symbols vs Strings
`symbols` are stored in memory only once and it makes things faster. Good for use in hashes. 

`Strings`, on the other hand, need to be stored every time it is used because it can change its content. 

```ruby 
"string".object_id == "string".object_id  #=> false

:symbol.object_id == :symbol.object_id    #=> true
```

_____

##References

+ [String Ruby Documentation] (https://ruby-doc.org/core-3.1.2/String.html)

+ [Literals Ruby Documentation] (https://ruby-doc.org/core-3.1.2/doc/syntax/literals_rdoc.html#label-Here+Document+Literals)

+ [String Literals] (https://www.thoughtco.com/string-literals-2908302)

+ [How to use heredoc in Ruby](https://www.rubyguides.com/2018/11/ruby-heredoc/)