개발자는 기록이 답이다
자바(Java) 알고리즘 문제풀이 입문: 코딩테스트 대비(문자열_암호) 본문
https://cote.inflearn.com/contest/10/problem/01-12
OnlineJudge
cote.inflearn.com
(위의 링크는 인프런 로그인 후, 해당 강의를 사지 않으면 접속이 되지 않습니다)
12. 암호
예시 입력 1
4
#****###**#####**#####**##**
예시 출력 1
COOL
내가 푼 풀이 (Time: 152ms Memory: 27MB)
1. replaceAll()함수로 특수문자를 1과 0으로 바꿔준다.
2. str을 7자리씩 떼서 list에 담아준다.
3. list를 순환하면서 아스키 넘버로 바꾼 뒤, String으로 형변환(cast)한다.
import java.util.ArrayList;
import java.util.Scanner;
public class Main {
public String solution(int num, String str) {
str = str.replaceAll("#", "1");
str = str .replaceAll("[*]", "0");
ArrayList<String> list = new ArrayList<>();
for (int i = 0; i < num; i++) {
int startIdx = i * 7;
list.add(str.substring(startIdx, startIdx + 7));
}
StringBuilder sb = new StringBuilder();
for (int i = 0; i < list.size() ; i++) {
int ascii = Integer.parseInt(list.get(i), 2);
String tmp = String.valueOf((char) ascii);
sb.append(tmp);
}
return sb.toString();
}
public static void main(String[] args) {
Main T = new Main();
Scanner sc = new Scanner(System.in);
int num = Integer.parseInt(sc.next());
String str = sc.next();
System.out.println(T.solution(num, str));
}
}
강의 답안 (Time: 164ms Memory: 27MB)
1. substring으로 잘라준걸 바로 replace로 변경한다.
2. StringValueOf()안써도 (char)만 해도 아스키코드가 알파벳으로 변경된다.
3. 2진수를 10진수로 변경할때는 Integer.parseInt()를 사용하면 된다.
4. str에 7를 잘라서 재할당한다.
import java.util.Scanner;
public class Main {
public String solution(int num, String str) {
String answer = "";
for (int i = 0; i < num; i++) {
String tmp = str.substring(0, 7).replace('#', '1').replace('*', '0');
int ascii = Integer.parseInt(tmp, 2);
answer += (char) ascii;
str = str.substring(7);
}
return answer;
}
public static void main(String[] args) {
Main T = new Main();
Scanner sc = new Scanner(System.in);
int num = sc.nextInt();
String str = sc.next();
System.out.println(T.solution(num, str));
}
}
성능 비교
주요 차이점은 다음과 같습니다:
1. 문자열 치환:
- 첫 번째 코드 조각은 replaceAll()을 두 번 사용하여 '#'을 '1'로, '*'을 '0'으로 대체합니다. 이 과정에서 대체가 이루어질 때마다 새 문자열을 생성합니다.
- 두 번째 코드 조각은 직접 replace()를 사용하여 '#' 및 '*' 문자를 대체합니다. 기존 문자열을 직접 수정하므로 더 효율적입니다.
2. ArrayList 대 직접 연결:
- 첫 번째 코드 조각은 ArrayList를 사용하여 중간 이진 서브 문자열을 저장하고 이들을 변환하고 추가하는 반면,
- 두 번째 코드 조각은 중간 데이터 구조 없이 'answer' 문자열에 변환된 문자를 직접 추가합니다.
3. 문자열 조작:
- 첫 번째 코드 조각은 substring()를 사용하여 입력 문자열에서 7자씩 서브 문자열을 추출하고 ArrayList에 저장합니다. 이로 인해 추가적인 메모리 및 문자열 조작 작업이 필요합니다.
- 두 번째 코드 조각은 반복적으로 str.substring(0, 7)를 사용하여 입력 문자열에서 7개의 문자를 추출하고, 그런 다음 str = str.substring(7)를 사용하여 해당 문자를 제거합니다. 중간 저장 공간을 사용하지 않습니다.
알고리즘 성능 측면에서:
두 번째 코드 조각은 중간 서브 문자열을 생성하고 ArrayList에 저장하는 작업을 피함으로써 메모리 사용이 더 효율적일 것입니다.두 번째 코드 조각은 문자열 조작을 보다 직접적으로 처리하므로 특히 큰 입력에 대해서 더 나은 성능을 제공할 수 있습니다.
일반적으로, 두 번째 코드 조각이 보다 효율적인 접근 방식을 가지고 있어 보입니다.
replace() vs replaceAll() 성능
- replace(): 정규식을 사용하지 않고 단순 문자열 대체를 수행하기 때문에 일반적으로 replaceAll()보다 더 빠른 성능을 보입니다.
- replaceAll(): 정규식을 사용하여 문자열을 대체하기 때문에 복잡한 패턴에 대해 치환이 이루어지며, 이로 인해 replace()에 비해 성능이 느릴 수 있습니다.
substring()함수의 메모리 낭비
- Java에서 substring()을 호출할 때 생성되는 문자열은 새로운 문자열 객체로 Heap 메모리 영역에 저장됩니다. 이렇게 하는 이유는 원래 문자열의 부분 문자열(substring)을 나타내기 위해 메모리 공간을 새롭게 할당해야 하기 때문입니다.
- 원래 문자열의 substring() 연산은 해당하는 인덱스 범위만큼의 문자를 복사하여 새로운 문자열을 생성합니다. 따라서 기존 문자열의 내용을 공유하면서도 새로운 문자열 객체를 만들어 사용하게 됩니다. 이는 문자열 연산 시 원본 문자열의 내용을 보존하면서 부분 문자열을 다룰 수 있도록 해줍니다.
참고 링크 :
https://developer-talk.tistory.com/690
[Java]특정 위치의 문자 변경하는 방법
특정 위치의 문자 변경하는 방법 문자열은 변경할 수 없는 클래스이므로, String 객체를 변경할 수 없습니다. 따라서, 특정 위치의 문자를 변경하기 위해서는 새로운 String 객체를 생성해야 합니다
developer-talk.tistory.com
[Java] replaceAll 대신 replace 사용하기
🙂 개요 String에서 흔히 사용하는 메서드 중에서는 replaceAll라는게 있다. 다들 알다시피 replaceAll은 특정 문자를 다른 문자로 대치할 수 있게 해주는 아주 편리한 메서드이다. 그러다 replaceAll보다
yeonyeon.tistory.com
https://velog.io/@m1naworld/Java-replace-vs-replaceAll
[Java] replace() vs replaceAll()
자바 스트링 관련 함수 중 특정 문자열을 원하는 문자열로 치환하는 함수 > replace() > > replaceAll() > 예제 위의 예제만 보면 두 함수의 차이점은 없어 보이지만,두 함수의 가장 큰 차이점은 입력 인
velog.io
https://codingdog.tistory.com/entry/java-replaceAll-메서드-그냥-쓰면-어떤-오버헤드가-걸릴까요
java replaceAll 메서드 : 그냥 쓰면 어떤 오버헤드가 걸릴까요?
String 클래스의 replaceAll 메서드는 상당히 많이 쓰는 메서드 중 하나입니다. 이것의 성능 문제에 대해서는, 이미 다른 곳에서도 많이 언급이 되기도 했습니다. 만.. 한 번 더 짚고 넘어가셔도 좋을
codingdog.tistory.com
https://hianna.tistory.com/527
[Java] 10진수 <-> 2진수, 8진수, 16진수로 변환하기
10진수 -> 2진수, 8진수, 16진수로 변환하기 java.lang.Integer의 toBinaryString(), toOctalString(), toHexaString() 메소드를 이용하여 10진수를 2진수, 8진수, 16진수 문자열로 변환할 수 있습니다. 리턴 타입 클래스
hianna.tistory.com
https://developer-talk.tistory.com/663
[Java]문자열에서 특수 문자 제거하는 방법
문자열에서 특수 문자 제거하는 방법 Java에서 언어(알파벳, 한글 등) 및 숫자를 제외한 나머지 문자는 특수 문자로 간주됩니다. !, @, #, $, %와 같은 문자를 특수 문자라고 합니다. 이번 포스팅은
developer-talk.tistory.com
'알고리즘 > 인프런 - Java알고리즘 입문' 카테고리의 다른 글
자바(Java) 알고리즘 문제풀이 입문: 코딩테스트 대비(Array_보이는 학생) (0) | 2023.09.04 |
---|---|
자바(Java) 알고리즘 문제풀이 입문: 코딩테스트 대비(Array_큰 수 출력하기) (0) | 2023.09.04 |
자바(Java) 알고리즘 문제풀이 입문: 코딩테스트 대비(문자열_문자열 압축) (0) | 2023.08.28 |
자바(Java) 알고리즘 문제풀이 입문: 코딩테스트 대비(문자열_가장 짧은 문자거리) (0) | 2023.08.28 |
자바(Java) 알고리즘 문제풀이 입문: 코딩테스트 대비(문자열_숫자만 추출) (0) | 2023.08.28 |