본문 바로가기
  • 더 넓은 세상을 바라보고 또 나 자신을 바라보며 그렇게 간격을 좁혀나가보자.
  • 이 길에 끝에서 바라던 나와 마주칠 수 있다면 난 너를 가득 안아줄거야.
IT 스터디/자바(JAVA)

Java 문자 입력

by Ryan Kim 2016. 4. 6.

관련 문서


System.in.read()

시스템으로부터 1바이트를 입력받아 정수형으로 리턴한다. 한글은 1바이트로 표현할 수 없기 때문에 숫자와 영문, 특수문자만 입력할 수 있다.

int input = System.in.read();
System.out.println(input);
 
→ 1을 입력하면 49 출력
cs

아스키코드로 변환된 문자를 원래 입력한 문자로 바꾸고 싶다면?

(char) input;  //1 입력, 1 출력
//혹은
char input = (char)System.in.read();
cs

System.in.read()를 사용하면서 주의할 점은 버퍼다. 콘솔에서 1을 입력했다고 해서 실제로 1만 입력되는 것이 아니라는 것인데:

1입력 → 1 + <엔터>

위처럼 <엔터>가 버퍼에 남아버려서 다음과 같은 현상이 발생한다:

System.in.read(); //입력대기
System.in.read(); //\r
System.in.read(); //\n
System.in.read(); //입력대기
cs

따라서 콘솔에서 연속으로 입력을 받아야 하는 경우엔 InputStream이 제공하는 skip() 메서드를 활용한다:

System.in.read();
System.in.skip(2);
System.in.read();
cs


BufferedReader

문자, 배열, 행을 버퍼에 담은 후 문자형 입력스트림으로 텍스트를 읽어 들인다.

read() : 1바이트를 읽어온다. 따라서 연속으로 사용하려면 버퍼초기화가 필요함. 
 //이 함수는 System.in.read()와 작동방식, 특징이 같음
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
 
br.read(); //입력대기
br.read(); //\r
br.read(); //\n
br.read(); //입력대기
cs

BufferedReader 또한 버퍼를 염두에 두고 사용해야 한다. read() 메서드는 사용자로부터 입력받은 입력버퍼를 한 문자씩만 반환한다. 버퍼가 비어있으면 새로 요구하고, 버퍼가 남아있으면 요구없이 스스로 다음 문자를 반환한다. 즉, 3문자를 입력하면 read를 다시 호출했을 때 입력값을 요청하는게 아닌 이미 입력된 문자 즉, 버퍼에서 값을 가져온다.

BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
 
System.out.println(br.read());
System.out.println(br.read());
System.out.println(br.read());
 
// 여기서 123을 입력하면
-> 49
-> 50
-> 51
cs

readLine()을 사용하면 버퍼초기화를 고려하지 않아도 되서 속편하다:

System.out.println(br.readLine());  // 입력대기
System.out.println(br.readLine());  // 입력대기
cs


Scanner

Scanner scan = new Scanner(System.in);
String str1 = scan.next();
String str2 = scan.next();
String str3 = scan.next();
 
// 여기서 a b c 를 입력하면
// 첫번째 next()는 a를,
// 두번째 next()는 b를,
// 세번째 next()는 c를 읽어옴.
cs

next(): 입력된 값 중 첫 단어만 읽어오며 나머지는 버퍼에 저장

nextLine() : 문자열(한 줄)을 읽는다. BufferedReader의 readLine()과 동일하다.

nextInt(), nextDouble(), 등 숫자형 데이터를 처리하는 메서드의 경우 문자열을 읽어 해당 데이터형으로 변환한다. next() 처럼 공백을 기준으로 첫 어절만 읽어오며 나머지는 버퍼로 처리한다. 숫자입력과 문자입력을 격리된 지역에서 각각 사용한다면 상관없지만 숫자입력 직 후 같은 지역 내에서 문자입력을 받는다면 버퍼문제가 발생한다. 앞서 말했듯이 next()의 파생형인 nextInt() 등의 메서드는 어절 단위로 읽어오기 떄문인데 만약 다음처럼:

int number = scn.nextInt();  // 여기서 123을 입력했다 가정
cs

일 경우엔 버퍼에 <엔터>가 남아있는 상태다.

여기서 다시:

String str = scn.nextLine();
cs

처럼 작성하면 nextLine()은 콘솔 입력을 기다리는게 아니라 버퍼에 있는 값을 가져오게 된다. 따라서 숫자형 입력을 받은 직후 다시 문자를 입력받아야 한다면 반드시 다음처럼 버퍼 초기화를 고려해야 한다:

int number = scn.nextInt();
scn.nextLine();   // 버퍼 초기화
String str = scn.nextLine();
cs


'IT 스터디 > 자바(JAVA)' 카테고리의 다른 글

자바의 sort를 정리  (0) 2024.11.16
자바에 난무하는 compare의 정리  (0) 2024.11.16
DecimalFormat 클래스  (0) 2016.02.14
BigIntger 클래스  (0) 2016.02.14
BigInteger 사용하기  (0) 2016.02.14