일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | 2 | 3 | ||||
4 | 5 | 6 | 7 | 8 | 9 | 10 |
11 | 12 | 13 | 14 | 15 | 16 | 17 |
18 | 19 | 20 | 21 | 22 | 23 | 24 |
25 | 26 | 27 | 28 | 29 | 30 | 31 |
- 유니온 파인드
- 백준 1806 자바
- 라이브커머스
- 다익스트라 최소비용구하기
- 자바 1193
- 2504 괄호의값 자바
- 백준 최소비용구하기 자바
- 1062번 가르침
- 이커머스
- 팀프로젝트
- 백준 1700 자바
- 줄세우기 위상정렬
- 커머스기사
- 백준 줄세우기 자바
- 웹 기술면접
- 백준 1193
- 자바 2869
- Spring Security
- 프로그래머스
- 백준 괄호의값 자바
- 괄호의값 스택
- 백준 2252 자바
- 기업분석
- 조인종류
- 인사관리사이트
- 백준 멀티탭스케줄링 자바
- 데이터베이스 기초지식
- 개발일지
- Union Find
- 온라인쇼핑
- Today
- Total
일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | 2 | 3 | ||||
4 | 5 | 6 | 7 | 8 | 9 | 10 |
11 | 12 | 13 | 14 | 15 | 16 | 17 |
18 | 19 | 20 | 21 | 22 | 23 | 24 |
25 | 26 | 27 | 28 | 29 | 30 | 31 |
- 유니온 파인드
- 백준 1806 자바
- 라이브커머스
- 다익스트라 최소비용구하기
- 자바 1193
- 2504 괄호의값 자바
- 백준 최소비용구하기 자바
- 1062번 가르침
- 이커머스
- 팀프로젝트
- 백준 1700 자바
- 줄세우기 위상정렬
- 커머스기사
- 백준 줄세우기 자바
- 웹 기술면접
- 백준 1193
- 자바 2869
- Spring Security
- 프로그래머스
- 백준 괄호의값 자바
- 괄호의값 스택
- 백준 2252 자바
- 기업분석
- 조인종류
- 인사관리사이트
- 백준 멀티탭스케줄링 자바
- 데이터베이스 기초지식
- 개발일지
- Union Find
- 온라인쇼핑
- Today
- Total
JumpUp
백준 [N1062 - 가르침] 본문
풀이과정
STEP1. 예외처리
최소 1개이상의 단어를 읽기 위해선 a, n, t, i, c 5개의 글자는 기본으로 가르쳐야합니다.
글자 5개미만이라면 0개의 단어를 읽을 수 있고 알파벳 26개의 글자를 모두가르친다면 N개의 단어를 읽을 수 있습니다.
이를 예외처리해주고 a, n, t, i, c외의 K-5개의 글자로 읽을 수 있는 단어의 개수를 구해봅니다.
STEP2. a, n, t, i, c 글자 제외 처리, 알파벳 방문처리
N개의 단어 각각 a, n, t, i, c를 제외해 String[] word배열에 저장합니다.
알파벳을 가르쳤는지 확인하기 위한 boolean[] visited배열을 선언하고 a, n, t, i, c는 가르쳤기에 true처리를 해줍니다.
STEP3. K-5개의 글자조합 구하기
가르칠 수 있는 글자조합을 구하는 방법은 2가지입니다.
(1) 글자 선택여부를 확인하는 visited배열 사용하기
combination매개변수에는 선택할 글자인덱스(=visited인덱스) alpha, 선택한 글자조합길이 len이 들어갑니다.
(2) 글자 선택여부를 확인하는 비트마스크 사용하기
아래와 같이 비트마스크의 원소 추가연산을 통해 가르친 a, n, t, i, c 표현합니다.
mask = 0;
mask |= 1 << 'a'-'a' ; // mask = 1
(a)
mask |= 1<<'n'-'a'; // mask = 1 1
(n) (a)
mask |= 1<<'t'-'a'; // mask = 1 1 1
(t) (n) (a)
mask |= 1<<'i'-'a'; // mask= 1 1 1 1
(t) (n) (i) (a)
mask |= 1<<'c'-'a'; // mask = 1 1 1 1 1
(t) (n) (i) (c) (a)
combination매개변수에는 글자조합길이 len, 비트마스크 시프트연산에사용될 start, 글자선택여부확인할 mask가 들어갑니다.
선택하지 않은 글자는 선택처리를 하고 다음에 선택할 글자를 찾기위해 재귀에 들어가게 됩니다. len이 k-5가 되면 글자조합이 완성됩니다. 구한 글자조합으로 최대 몇개의 단어를 읽을 수 있는지 max변수를 통해 출력합니다.
소스코드
(1) visited배열 사용하기
public class 가르침 {
private static int N, K;
private static String[] word;
private static boolean[] visitied = new boolean[26];
private static int max = Integer.MIN_VALUE;
public static void main(String[] args) throws IOException {
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
StringTokenizer st = new StringTokenizer(br.readLine());
N = Integer.parseInt(st.nextToken());
K = Integer.parseInt(st.nextToken());
if(K<5) {
System.out.println("0");
return;
}
else if(K==26) {
System.out.println(N);
return;
}
else {
//a,n,t,i,c 필수로 가르치기에 가르칠 수 있는 K-5개 글자에서 제외
word= new String[N];
for (int i = 0; i < N; i++) {
String str = br.readLine().replaceAll("[a,n,t,i,c]", "");
word[i] = str;
}
visitied['a'-'a'] = true;
visitied['n'-'a'] = true;
visitied['t'-'a'] = true;
visitied['i'-'a'] = true;
visitied['c'-'a'] = true;
//k-5개의 글자조합
combination(0,0);
System.out.println(max);
}
br.close();
}
private static void combination(int alpha, int len) {
if(len==K-5){
int cnt = 0;
for(int i=0;i<N;i++){
boolean read = true;
for(int j=0;j<word[i].length();j++){
if(!visitied[word[i].charAt(j)-'a']){
read = false;
break;
}
}
if(read) cnt++;
}
max = Math.max(max, cnt);
return;
}
for(int i=alpha;i<26;i++){
if(!visitied[i]){
visitied[i] = true;
combination(i,len+1);
visitied[i] = false;
}
}
}
}
(2) 비트마스크 사용하기
public class 가르침 {
private static int N, K;
private static String[] word;
private static int mask;
private static int max = Integer.MIN_VALUE;
public static void main(String[] args) throws IOException {
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
StringTokenizer st = new StringTokenizer(br.readLine());
N = Integer.parseInt(st.nextToken());
K = Integer.parseInt(st.nextToken());
if(K<5) {
System.out.println("0");
return;
}
else if(K==26) {
System.out.println(N);
return;
}
else {
//a,n,t,i,c 필수로 가르치기에 가르칠 수 있는 K-5개 글자에서 제외
word= new String[N];
for (int i = 0; i < N; i++) {
String str = br.readLine().replaceAll("[a,n,t,i,c]", "");
word[i] = str;
}
//k-5개의 글자조합
mask = 0;
mask |= 1<<'a'-'a';
mask |= 1<<'n'-'a';
mask |= 1<<'t'-'a';
mask |= 1<<'i'-'a';
mask |= 1<<'c'-'a';
combination(0, 1, mask);
System.out.println(max);
}
br.close();
}
private static void combination(int len, int start, int mask) {
if(len==K-5){
int cnt = 0;
for(int i=0;i<N;i++){
boolean read = true;
for(int j=0;j<word[i].length();j++){
if((mask&(1<<word[i].charAt(j)-'a'))==0){
read = false;
break;
}
}
if(read) cnt++;
}
max = Math.max(max, cnt);
return;
}
for(int i=start;i<26;i++){
if((mask&(1<<i))!=0) continue;
combination(len+1, i+1, mask | 1<<i);
}
}
}
'알고리즘' 카테고리의 다른 글
백준 [N1806 - 부분합] (0) | 2021.12.29 |
---|---|
백준 [N1700 - 멀티탭스케줄링] (0) | 2021.12.27 |
백준 [N2504 - 괄호의값] (0) | 2021.12.17 |
백준 [N14888 - 연산자끼워넣기] (0) | 2021.12.04 |
프로그래머스 [여행경로] (0) | 2021.11.20 |