728x90
문제
https://www.codetree.ai/problems/decimal-and-binary-number?&utm_source=clipboard&utm_medium=text
코드트리 | 코딩테스트 준비를 위한 알고리즘 정석
국가대표가 만든 코딩 공부의 가이드북 코딩 왕초보부터 꿈의 직장 코테 합격까지, 국가대표가 엄선한 커리큘럼으로 준비해보세요.
www.codetree.ai
코드
첫 번째 줄에 이진수 N을 입력받아 십진수로 변환한 값에 17을 곱한 후 다시 이진수로 변환하여 출력하는 문제다.
- N은 최대 1000 자릿수까지 공백 없이 주어진다.
큰 숫자의 연산이 필요할 때 사용하는 BigInteger를 통해 쉽게 구현할 수 있다.
public class Main {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
String n = sc.next();
BigInteger decimal = new BigInteger(n, 2); // 10진수로 변환
BigInteger binary = decimal.multiply(BigInteger.valueOf(17)); // 17 곱하기
System.out.println(binary.toString(2)); // 2진수로 변환하여 출력
}
}
위와 같이 BigInteger를 활용해 쉽게 문제를 해결하였지만 문제가 의도한 대로 푼 것 같지 않은 찝찝함이 남아 있었다.
곰곰이 생각해 보니 2진수의 값을 왼쪽으로 shift 할 때마다 2배씩 증가한다는 사실을 깨달았다. 이로써 직접 구현하여 풀 수 있었다.
import java.util.Scanner;
public class Main {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
String n = sc.next();
// 왼쪽으로 4번 shift(16배)
String shift = n + "0000";
// 자리수 맞추기
n = "0000" + n;
// carry 연산을 위한 변수
int carry = 0;
// 결과를 담을 StringBuilder
StringBuilder result = new StringBuilder();
// n 역순으로 반복
for (int i = n.length() - 1; i >= 0; i--) {
int a = n.charAt(i) - '0';
int b = shift.charAt(i) - '0';
int sum = a + b + carry;
// 이진수 계산
if (sum % 2 == 0) {
result.insert(0, "0");
} else {
result.insert(0, "1");
}
// carry 연산
if (sum >= 2) {
carry = 1;
} else {
carry = 0;
}
}
// carry가 남아있으면 "1" 붙임
if (carry == 1) {
result.insert(0, "1");
}
System.out.println(result);
}
}
- 2진수의 shift 연산과 덧셈 시 발생하는 carry 연산에 대해서 이해하면 풀기 쉽다.
- 2진수의 특성상 왼쪽으로 이동할 때마다 2배씩 증가한다. (타입의 범위로 인해 항상 그런 것만은 아님)
- 입력받은 n 문자열 뒤에 "0000"(왼쪽으로 4번 shift)을 붙여줌으로써 16배가 된다.
- n에 "0000"을 더한 문자열 shift와 입력받은 문자열 n을 더하면 정확히 17배가 된다. 반복문 인덱스를 맞추기 위해 n에 문자열 "0000"을 더한다.
- 반복문을 통해 n과 shift 문자열의 각 자릿수와 캐리 연산을 위한 carry 변수를 더한다.
- 더한 값을 2로 나눈 나머지가 1이면 "1", 0이면 "0"을 StringBuilder의 첫 번째 인덱스에 추가한다.
- 더한 값이 2 이상인 경우 carry를 1, 아닌 경우 0으로 변경한 뒤 위 연산을 반복한다.
- 마지막에 carry가 남아있으면 "1"을 첫 번째 인덱스에 추가한 후 이를 출력한다.
728x90