rubyguides

String#chomp

chomp removes trailing line separators from a string. It handles the common line-ending styles (Unix LF, old Mac CR, Windows CRLF) and lets you specify custom separators.

Signature

str.chomp(separator=$/) → new_string

Parameters:

  • separator — the string to remove from the end. Defaults to $/ (the input record separator, typically "\n").

Returns: A new string with the trailing separator removed, or the original string if no separator matches.

Default Behavior

With no argument, chomp removes "\n", "\r", or "\r\n" from the end:

"hello\n".chomp
# => "hello"

"hello\r\n".chomp
# => "hello"

"hello\r".chomp
# => "hello"

If the string doesn’t end with the separator, chomp returns a copy unchanged:

"hello".chomp
# => "hello"

Custom Separators

Pass a string to remove a specific trailing sequence:

"hello\n\n".chomp("\n")
# => "hello\n"

"data.txt\r\n".chomp("\r\n")
# => "data.txt"

"hello!!!".chomp("!!!")
# => "hello"

Multiple occurrences are removed only from the end:

"hello!!!".chomp("!")
# => "hello!!"

"hello!!!".chomp("!!!")
# => "hello"

The Bang Variant

chomp! modifies the receiver in place:

s = "hello\n"
s.chomp!
# => "hello"
s
# => "hello"

# Returns nil if nothing to chomp:
s2 = "hello"
s2.chomp!
# => nil
s2
# => "hello"

Practical Examples

Reading Lines from a File

The most common use is cleaning up lines read from a file or stdin:

File.readlines("config.txt").each do |line|
  # Without chomp, line includes the trailing "\n"
  puts line.chomp
end

Parsing Multi-Line Input

input = "alice,bob,charlie\n"

name, rest = input.chomp.split(",", 2)
name
# => "alice"
rest
# => "bob,charlie"

Avoiding Nil When There’s No Newline

Unlike strip, chomp never returns nil when given no argument — it always returns a string:

"no newline here".chomp
# => "no newline here" (a copy, not nil)

Special Separator Values

Empty String

An empty string separator removes no characters:

"hello\n".chomp("")
# => "hello\n" (unchanged)

Nil

Passing nil removes nothing — returns a copy of the string:

"hello\n".chomp(nil)
# => "hello\n" (unchanged)

Custom Multi-Character Separator

record = "field1,field2,field3---"
record.chomp("---")
# => "field1,field2,field3"

Common Pitfalls

CRLF on Different Systems

If your input has Windows line endings ("\r\n") but you’re running on Unix, chomp handles them automatically:

# On Unix, reading a file with CRLF:
content = File.read("windows_file.txt")
content.chomp
# removes the \n, leaving \r at the end
# => "line with trailing \r"

For reliable cross-platform handling, consider:

content.gsub(/\r\n?/, "\n").chomp

chomp vs strip

chomp only removes line endings. strip removes all whitespace from both ends:

"  hello  \n".chomp
# => "  hello  " (spaces preserved)

"  hello  \n".strip
# => "hello" (spaces removed too)

chomp! Returns nil on No Match

Unlike some bang methods, chomp! returns nil (not the string) when no separator is present:

result = "no newline".chomp!
# result is nil, not "no newline"
# This matters in conditional expressions

See Also