Ruby로 프로그램을 작성하다 보면 사용자에게 질문을 하고 싶은 순간이 찾아옵니다.
어떻게 하면 될까요?
바로 Ruby의 gets 메서드를 사용하면 사용자 입력을 읽어올 수 있습니다.
gets를 호출하면 프로그램이 잠시 멈추고, 키보드로 무언가를 입력한 후 엔터 키를 누르기를 기다립니다.
그 결과는?
문자열이 반환됩니다. 이 문자열에는 입력된 내용이 그대로 담겨 있기 때문에, 변수에 할당하면 자유롭게 활용할 수 있습니다.
가장 대표적인 예제는 바로 인사 프로그램입니다.
코드는 다음과 같습니다:
name = gets.chomp
puts "Hello #{name}, nice to meet you!"
#{name}처럼 문자열 안에 변수를 넣는 기법을 문자열 인터폴레이션(string interpolation)이라고 부릅니다.
직접 실행해 보면서 동작 방식을 확인해 보세요.
- 먼저 위 코드를 "greeting.rb" 파일로 저장합니다.
- 그다음 터미널에서 "ruby greeting.rb" 명령어로 실행합니다.
이름을 입력하면 프로그램이 여러분을 맞이해 줄 겁니다!
꽤 멋지죠?
자, 그런데:
도대체 chomp는 왜 붙여야 하는 걸까요?
chomp는 gets의 결과를 아주 특정한 방식으로 바꿔주는 Ruby 메서드입니다.
한번 지워 보세요. 앞의 점(.)까지 포함해서 name = gets.chomp를 name = gets로 바꿔 보는 겁니다.
코드를 저장하고 다시 실행하면...
인사말이 한 줄에 출력되지 않고 두 줄로 나뉘어 버리는 것을 발견하게 될 겁니다.
왜 이런 일이 생길까요?
지금부터 자세히 파헤쳐 보겠습니다!
줄바꿈 문자와 특수 문자 이해하기
Ruby는 gets 메서드가 활성화되어 있는 동안 입력된 모든 내용을 읽어들입니다.
앞선 인사 프로그램의 경우라면 여러분의 이름뿐만 아니라,
인사말을 두 줄로 만들어버리는 특별한 "줄바꿈(new line)" 문자까지 함께 읽힙니다.
바로 이 줄바꿈 문자입니다:
\n
이런 종류의 특수 문자들은 평소에는 눈에 보이지 않으며, 줄바꿈이나 공백 등의 형태로만 존재합니다.
만약 눈으로 직접 확인하고 싶다면... 가격 1억 원짜리 마법 손전등이 필요합니다.
농담입니다!
실제로 필요한 건 p 메서드 또는 inspect 메서드뿐입니다.
사용 예시:
p name # "Jesus\n"
보이시나요? 바로 저 "줄바꿈" 문자(\n)입니다.
이제 처음 질문으로 돌아가 볼까요...
chomp는 도대체 어떤 역할을 할까요?
chomp의 목적은 문자열 끝에 붙은 줄바꿈 문자를 제거하는 것입니다.
직접 확인해 봤듯이, 이것이 얼마나 유용한지 아셨을 겁니다!
또 다른 예제
줄바꿈 문자나 다른 특수 문자가 미치는 영향은 단순히 출력 결과의 모양에만 국한되지 않습니다.
if문에도 영향을 줄 수 있습니다.
예제:
name = gets if name == "David" puts "Hello David, we were expecting you!" end
위 코드에서 gets에 chomp를 사용하지 않으면, 줄바꿈 문자(\n) 때문에 두 문자열이 같지 않게 되어 조건문은 false로 평가됩니다.
참고로...
이 문제는 gets 외부에서 가져온 문자열에도 똑같이 적용됩니다. 데이터베이스나 파일, 혹은 다른 소스에서 읽어온 데이터 역시 예외가 아닙니다.
항상 특수 문자의 존재를 주의 깊게 살펴보세요!
chomp vs chop vs strip 비교
사용자 입력을 정리할 때 유용하게 쓸 수 있는 메서드가 두 개 더 있습니다. 바로 chop과 strip입니다.
strip은 문자열 앞뒤의 공백(whitespace)을 제거합니다.
예제:
" John Smith ".strip
chop은 항상 문자열의 마지막 문자 하나를 제거합니다.
첫 번째 문자 제거하기
반대로 문자열의 시작 부분에서 문자를 제거해야 할 때도 있습니다.
이렇게 하면 됩니다:
str = "Mr. John" str[0..3] = "" str # "John"
이 코드는 앞의 네 글자를 제거합니다.
gets 메서드가 두 개라고? 상황이 복잡해집니다!
특수한 경우가 하나 있습니다.
단순히 gets 대신 $stdin.gets를 사용해야 하는 경우입니다.
다음과 같은 에러가 발생한다면:
`gets': No such file or directory @ rb_sysopen
왜 이런 일이 생길까요?
gets 메서드에는 두 가지 버전이 존재하기 때문입니다.
- 기본 버전: 파일 이름을 읽으려고 시도합니다.
- 대체 버전(
$stdin.gets): 항상 사용자 입력에서 읽어옵니다.
이제 알겠죠? gets 사용 중에 이런 에러가 보이면 $stdin.gets로 바꿔보면 해결됩니다.
정리
이번 글에서는 gets와 chomp 메서드가 각각 무엇을 하는지, 어떻게 동작하는지, 그리고 왜 유용한지 배웠습니다.
추가로 strip, chop 같은 문자열 정리 메서드와 $stdin.gets의 특수 사례까지 함께 살펴봤습니다.
계속해서 Ruby 튜토리얼로 학습을 이어가 보세요.
읽어주셔서 감사합니다! 🙂