프로그래밍풀스택 개발자

Rust에서 문자열을 숫자로 읽고 파싱하는 방법(예: String에서 i32로 변환) 설명해 주세요. parse 메서드를 사용할 때 어떤 함정이 있는지, 변환 오류를 올바르게 처리하는 방법은 무엇인지요?

Hintsage AI 어시스턴트로 면접 통과

답변

Rust는 FromStr 트레이트를 통해 문자열을 숫자로 변환할 수 있는 편리한 표준 도구를 제공합니다. 가장 많이 사용되는 방법은 문자열과 슬라이스에서 호출할 수 있는 .parse::<T>() 메서드입니다.

질문의 배경

많은 언어에서 문자열을 숫자로 변환하는 것은 일반적인 업무이지만, Rust에서는 최대한 안전하고 투명하게 수행됩니다. 오류 처리는 표준 라이브러리의 계약의 일부이지 런타임 예외가 아닙니다.

문제점

.parse::<T>()Result<T, ParseIntError> 유형의 결과를 반환하므로 실패를 명시적으로 처리해야 합니다. 흔한 오류는 오류 가능성을 무시하고 분석 없이 unwrap()을 사용하는 것으로, 이는 잘못된 데이터 입력 시 프로그램이 충돌하는 위험을 초래합니다.

해결책

문자열 변환을 위해 parse 메서드를 사용합니다. 그 서명은 다음과 같습니다:

let num: i32 = "42".parse().unwrap();

하지만 올바르게 오류를 처리하는 것이 더 좋습니다:

let s = "abc"; match s.parse::<i32>() { Ok(n) => println!("숫자가 수신되었습니다: {}", n), Err(e) => println!("파싱 오류: {e}"), }

주요 특징:

  • 각 숫자 유형에 대해 FromStr이 구현되어 있지만, 정확한 제한은 명시적이지 않습니다: 공백, 부호, 오버플로우는 다르게 처리됩니다.
  • 오류는 패닉이나 예외가 아닌 Result로 반환됩니다.
  • FromStr을 구현한 모든 유형(사용자 정의 유형 포함)은 .parse()의 대상이 될 수 있습니다.

함정이 있는 질문들.

결과 유형을 지정하지 않고 parse를 사용할 수 있습니까?

아니요, 유형을 명시하지 않거나 암시적으로 유추하지 않으면 Rust는 어떤 유형으로 변환해야 할지 이해하지 못해 오류가 발생합니다.

숫자가 아닌 내용이 포함된 문자열을 숫자로 변환하려고 하면 어떻게 됩니까?

메서드는 오류(Err(...))를 반환하며 패닉을 유발하지 않습니다. 오류는 Debug 트레이트를 구현하므로 출력에 유용합니다.

let num: Result<u32, _> = "not_a_number".parse(); assert!(num.is_err());

내용이 확실한 경우 parse 이후에 unwrap을 사용할 수 있습니까?

기술적으로 가능하지만 이는 안티 패턴입니다. 문자열이 예상치 않게 유효하지 않을 경우 프로그램이 강제로 종료됩니다.

일반적인 오류 및 안티 패턴

  • 오류 처리가 없는 unwrap() 사용
  • 사용자 입력 전에 변환 시 trim 미사용
  • 변환할 때 유형 오류(parse::<String>()) 발생

실제 사례

부정적 케이스

콘솔 유틸리티가 사용자로부터 숫자를 읽고 .parse().unwrap()을 사용합니다. 우연히 잘못된 입력이 발생하면 프로그램이 갑자기 종료되며 사용자는 그 원인을 이해하지 못합니다.

장점:

  • 코드가 간단합니다.

단점:

  • 프로그램의 잠재적 종료, 나쁜 사용자 경험

긍정적 케이스

입력은 먼저 공백이 제거되고, parse는 match 시나리오에서 사용되거나 필요한 경우 자신의 오류를 반환하기 위해 map_err를 사용합니다. 오류가 적절하게 처리되고 명확한 오류 메시지가 출력됩니다.

장점:

  • 잘못된 입력 시 프로그램이 종료되지 않으며 오류가 유익합니다.
  • 코드가 더 안전하고 명확하게 유지 가능합니다.

단점:

  • 입력 처리 시 코드가 약간 더 많아집니다.