Ruby Symbols
Efficient immutable identifiers in Ruby
🔖 What are Ruby Symbols?
Symbols are immutable, reusable identifiers prefixed with a colon (:). They're more memory-efficient than strings because each symbol is stored only once in memory, making them perfect for hash keys and constants.
# Creating symbols
name = :john
status = :active
puts name # Output: john
puts status # Output: active
Output:
john
active
Symbol Concepts
Memory Efficient
Stored once in memory
:name.object_id
:name.object_id
# Same ID!
Immutable
Cannot be changed
sym = :hello
# sym cannot be modified
Hash Keys
Perfect for hash keys
user = { name: "Bob" }
puts user[:name]
Conversion
Convert to/from strings
:hello.to_s
"hello".to_sym
🔹 Creating Symbols
Symbols are created by prefixing a name with a colon. They look like variables but behave differently. Once created, a symbol with the same name always refers to the same object in memory, unlike strings which create new objects each time.
# Simple symbols
first_name = :john
last_name = :doe
status = :active
# Symbols with underscores
user_type = :admin
is_verified = :true
# Symbols in arrays
colors = [:red, :green, :blue]
puts first_name # Output: john
puts colors[0] # Output: red
Output:
john
red
🔹 Symbols vs Strings
Symbols and strings may look similar but have key differences. Strings are mutable and create new objects each time, while symbols are immutable and reuse the same object. This makes symbols faster and more memory-efficient for identifiers and hash keys.
# Strings create new objects
string1 = "hello"
string2 = "hello"
puts string1.object_id == string2.object_id # Output: false
# Symbols reuse the same object
symbol1 = :hello
symbol2 = :hello
puts symbol1.object_id == symbol2.object_id # Output: true
# Memory comparison
puts "hello".object_id # Different each time
puts "hello".object_id # Different ID
puts :hello.object_id # Same each time
puts :hello.object_id # Same ID
Output:
false
true
🔹 Symbols as Hash Keys
Symbols are the preferred choice for hash keys in Ruby because they're faster to compare and use less memory. Modern Ruby syntax allows you to write symbol keys without the hash rocket (=>), making code cleaner and more readable.
# Old syntax with hash rocket
person = { :name => "Alice", :age => 25 }
# Modern syntax (preferred)
person = { name: "Alice", age: 25, city: "Boston" }
# Accessing values
puts person[:name] # Output: Alice
puts person[:age] # Output: 25
# Mixed example
config = {
host: "localhost",
port: 3000,
debug: true
}
puts config[:host] # Output: localhost
Output:
Alice
25
localhost
🔹 Converting Between Symbols and Strings
Ruby provides simple methods to convert between symbols and strings. Use to_s to convert a symbol to a string, and to_sym or intern to convert a string to a symbol. This is useful when working with user input or external data.
# Symbol to string
symbol = :hello
string = symbol.to_s
puts string # Output: hello
puts string.class # Output: String
# String to symbol
text = "world"
sym = text.to_sym
puts sym # Output: world
puts sym.class # Output: Symbol
# Alternative method
sym2 = "ruby".intern
puts sym2 # Output: ruby
# Practical example
user_input = "name"
hash_key = user_input.to_sym
person = { name: "Bob" }
puts person[hash_key] # Output: Bob
Output:
hello
String
world
Symbol
ruby
Bob
🔹 When to Use Symbols
Use symbols for identifiers that won't change, like hash keys, method names, or status values. Use strings for text that might be modified or displayed to users. Symbols are ideal for internal code labels, while strings are better for user-facing content.
# Good use of symbols
user = {
name: "Alice", # Symbol key
role: :admin, # Symbol value for status
status: :active
}
# Good use of strings
message = "Hello, #{user[:name]}!" # String for display
puts message # Output: Hello, Alice!
# Symbols for method parameters
def greet(person:, greeting: :formal)
if greeting == :formal
puts "Good day, #{person}"
else
puts "Hey #{person}!"
end
end
greet(person: "Bob", greeting: :casual) # Output: Hey Bob!
Output:
Hello, Alice!
Hey Bob!