2022.02.10 네이버 블로그에 작성했던 것!
|contains|문자열에 검색하고자 하는 문자가 있는지 확인 / 포함:true 미포함:false|
|indexOf|문자열에서 검색하는 문자의 위치를 반환 / 포함:문자 위치 미포함:-1|
|matches|정규식을 이용하여 문자열을 검색한다./ 특정 문자열을 검색할 때 사용하기보다는 한글, 숫자와 같이 해당 형태의 텍스트가 존재하는지 확인할 때 사용하면 좋다./ 포함:true 미포함:false|
package 백준문자열;
import java.util.*;
public class 알파벳찾기 {
public static void main(String[] args) {
// TODO Auto-generated method stub
Scanner sc= new Scanner(System.in);
String str=sc.next();
for(char c='a';c<='z';c++) {
System.out.print(str.indexOf(c)+" ");
}
}
}
구글링해서 찾아낸 다른 분 코드
import java.util.Scanner;
public class Main {
public static void main(String[] args) {
Scanner in = new Scanner(System.in);
int[] arr = new int[26];
for(int i = 0; i < arr.length; i++) {
arr[i] = -1;
}
String S = in.nextLine();
for(int i = 0; i < S.length(); i++) {
char ch = S.charAt(i);
if(arr[ch - 'a'] == -1) { // arr 원소 값이 -1 인 경우에만 초기화
arr[ch - 'a'] = i;
}
}
for(int val : arr) { // 배열 출력
System.out.print(val + " ");
}
}
}
그다음 Scanner 받아서 S 문자열을 문자 ch로 받고
arr[ch-'a']=i로 ch의 문자 위치를 arr 배열 값으로 바꿈
if문에서 arr[ch-'a']==-1라는 조건을 추가해서 ch에 해당하는 문자가 있을 떄만 i로 바꾸게 함
동일한 문자가 나올 땐 걱정 ㄴㄴ 이미 앞선 동일 문자 값을 i로 바꿨기 때문에..
package 백준문자열;
import java.util.*;
public class 문자열반복 {
public static void main(String[] args) {
// TODO Auto-generated method stub
Scanner sc = new Scanner(System.in);
int n = sc.nextInt();
for(int i=0;i<n;i++) {
int R=sc.nextInt();
String S=sc.next();
for(int j=0;j<S.length();j++) {
for(int k=0;k<R;k++)
{System.out.print(S.charAt(j));}
}
System.out.println();
}
}
}
놓친 부분:
1.배열 굳이 안사용해도 괜찮은데 사용하려해서 헷갈림
2. 문자열에도 length() 사용 가능하군
3. for문 속 for문 속 for문도 가능했군 ,,,,,,,, 젤 안 속 for문을 간과함
4.무엇보다 입력 부분에서 2 3 ABC 5 /HTP0라고 연달아 입력해야하는 줄 알고 안쪽 for문을 안쓸뻔
import java.util.*;
public class 단어의개수 {
public static void main(String[] args) {
// TODO Auto-generated method stub
Scanner sc = new Scanner(System.in);
String str=sc.nextLine();
String[] arr=str.trim().split(" "); //trim은 앞 뒤 공백만 없애줌
System.out.println(arr.length);
}
}
위에는 나의 틀린 풀이,,
import java.util.*;
public class 단어의개수 {
public static void main(String[] args) {
// TODO Auto-generated method stub
Scanner sc = new Scanner(System.in);
String str=sc.nextLine();
String[] arr=str.trim().split(" "); //trim은 앞 뒤 공백만 없애줌
if(arr[0].length() == 0) {
System.out.println(0);
return;
}
System.out.println(arr.length);
}
}
맞은 풀이
공백만 존재하는 단어가 있을 때 틀릴 수 있으니 if문 조건 넣고
arr[0].length() == 0와 같이 공백 여부 확인함
package 백준문자열;
import java.util.*;
public class 다이얼 {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
String num=sc.next();
int cnt=0;
for(int i=0;i<num.length();i++) {
switch(num.charAt(i)) {
case 'A':
case 'B':
case 'C':cnt+=3;
break;
case 'D':
case 'E':
case 'F':cnt+=4;
break;
case 'G':
case 'H':
case 'I':cnt+=5;
break;
case 'J':
case 'K':
case 'L':cnt+=6;
break;
case 'M':
case 'N':
case 'O':cnt+=7;
break;
case 'P':
case 'Q':
case 'R':
case 'S':cnt+=8;
break;
case 'T':
case 'U':
case 'V':cnt+=9;
break;
case 'W':
case 'X':
case 'Y':
case 'Z':cnt+=10;
break;
}
}
System.out.println(cnt);
}
}
내 코드
switch case 문에서 자바에서는 case 'A', 'B', 'C': 이런 식으로 해도 돼서 백준에 입력했더니 컴파일 에러 계속 뜸.. 중복되었다고..
그래서 저리 바꿈
import java.util.Scanner;
public class Main {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
String str = sc.next();
// 문자열을 char형 배열로 반환
char[] chars = str.toCharArray();
// 총 걸리는 시간을 저장할 int형 변수
int sum = 0;
// foreach 반복문, char[] 배열 안에 값들을 하나씩 char형으로 처리
for (char c : chars) {
// 알파벳이 ABC 중 하나라면 + 3초
if (c >= 'A' && c <= 'C') {
sum += 3;
// 알파벳이 DEF 중 하나라면 + 4초
} else if (c >= 'D' && c <= 'F'){
sum +=4;
// 알파벳이 GHI 중 하나라면 + 5초
} else if (c >= 'G' && c <= 'I'){
sum +=5;
// 알파벳이 JKL 중 하나라면 + 6초
}else if (c >= 'J' && c <= 'L'){
sum +=6;
// 알파벳이 MNO 중 하나라면 + 7초
}else if (c >= 'M' && c <= 'O'){
sum +=7;
// 알파벳이 PQRS 중 하나라면 + 8초
}else if (c >= 'P' && c <= 'S'){
sum +=8;
// 알파벳이 TUV 중 하나라면 + 9초
}else if (c >= 'T' && c <= 'V'){
sum +=9;
// 알파벳이 WXYZ 중 하나라면 + 10초
}else if (c >= 'W' && c <= 'Z'){
sum +=10;
}
}
System.out.println(sum);
}
}
if문 사용한 다른 분 답
package 백준배열;
import java.util.Scanner;
public class 그룹단어체커 {
public static void main(String[] args) {
// TODO Auto-generated method stub
Scanner sc = new Scanner(System.in);
int n=sc.nextInt();
int num=0, cnt=0;
String[] arr=new String[3];
for(int i=0;i<n;i++) {
arr[i]=sc.next();
char ch=arr[i].charAt(0);
for(int j=i+1;j<n;j++) {
if(arr[i-1]!=arr[i]) {
cnt=1;
if(arr[i]==arr[j]) {
cnt=0;
}
}
else {
cnt=1;
if(arr[i-1]!=arr[i]) {
if(arr[i]==arr[j]) {
cnt=0;
}
}
}
}
num+=cnt;
System.out.println(num);
}
}
}
내가 짠 코드
if문으로 고려해서 하면 될 거 같았는데 생각보다 케이스가 많다
구글링해서 본 코드는 boolean 함수를 이용해서 그룹단어인지 아닌지 여부만 판단!
import java.util.Scanner;
public class Main {
static Scanner in = new Scanner(System.in);
public static void main(String[] args) {
int count = 0;
int N = in.nextInt();
for (int i = 0; i < N; i++) {
if (check() == true) {
count++;
}
}
System.out.println(count);
}
public static boolean check() {
boolean[] check = new boolean[26];
int prev = 0;
String str = in.next();
for(int i = 0; i < str.length(); i++) {
int now = str.charAt(i); // i 번째 문자 저장 (현재 문자)
// 앞선 문자와 i 번째 문자가 같지 않다면?
if (prev != now) {
// 해당 문자가 처음 나오는 경우 (false 인 경우)
if ( check[now - 'a'] == false ) {
check[now - 'a'] = true; // true 로 바꿔준다
prev = now; // 다음 턴을 위해 prev 도 바꿔준다
}
// 해당 문자가 이미 나온 적이 있는 경우 (그룹단어가 아니게 됨)
else {
return false; //함수 종료
}
}
// 앞선 문자와 i 번째 문자가 같다면? (연속된 문자)
// else 문은 없어도 됨
else {
continue;
}
}
return true;
}
}
알고리즘에서 가장 중요하게 작용할 변수 prev 를 생성한다.
prev 의 역할은 이후 반복문에서 문자를 꺼내올 때 앞선 문자와 연속되는지, 아닌지를 판별하기 위함이다.
즉, 아래와 같이 돌아가도록 할 것이다.
prev 의 문자와 해당 문자가 같다면?
→ 해당 문자가 중복된 문자인지 여부를 검사하지 않는다. (boolean 배열)
prev 의 문자와 해당 문자가 다르다면?
→ 해당 문자가 중복된 문자인지 여부를 검사한다. (boolean 배열)
주의할 점!
메인 함수와 check 함수에서도 Scanner 을 쓰므로 반드시 main 함수 밖에 전역 변수로 static 을 붙여 Scanner 을 생성해주어야 한다.
또한 문자열을 입력받을 때 nextLine() 을 쓰면 에러 난다. (개행이 버퍼에 남아있어서 다음 입력때 개행이 str 에 저장된다.)
놓친 부분:
1. boolean 함수로 그룹단어 체크 여부를 참/거짓으로 판단할 줄이야..
2. 단어만 받을 수 있다는 생각이 들어 char ch 이렇게 변수를 설정했는데, int 와 같이 아스키코드를 이용하여 숫자로 간편하게 비교할 수 있다니..!
3. boolean 배열에 원소 있고 없고 여부를 true/false로 생각하면 함수 이용해서 구하기 쉽다
4. 함수 속 '다음 부분 설정 위해 prev=now로 설정하는 거 놓치면 x
5.check[now-'a'] 배열은 중복 여부를 확인해줄 수 있는 boolean 배열이다.
ex) aba 단어 넣으면 세번째 a에서 true 값이 이미 나온 상태
package 백준배열;
import java.util.Scanner;
public class 단어공부 {
public static void main(String[] args) {
Scanner sc=new Scanner(System.in);
String str=sc.next();
String strup=str.toUpperCase();
int[] count=new int[26];
char most='a';
int num=0;
String Alphabet="ABCDEFGHIJKLMNOPQRSTUVWXYZ";
for(int i=0;i<str.length();i++) {
for(int j=0;j<Alphabet.length();j++) {
if(strup.charAt(i)==Alphabet.charAt(j)) {
count[j]+=1;
}
if(count[j]>num) {
most=Alphabet.charAt(j);
num=count[j];
}
}
for(int m=0;m<Alphabet.length();m++) {
for(int n=m+1;n<Alphabet.length();n++) {
if(count[m]!=0) {
if(count[m]==count[n]&&count[m]==num) {
most='?';
}
}
}
}
}
System.out.println(most);
}
}
노가다 끝에 맞췄다!
import java.util.Scanner;
public class Main {
public static void main(String[] args) {
Scanner in = new Scanner(System.in);
int[] arr = new int[26]; // 영문자의 개수는 26개임
String s = in.next();
for (int i = 0; i < s.length(); i++){
if ('A' <= s.charAt(i) && s.charAt(i) <= 'Z') { // 대문자 범위
arr[s.charAt(i) - 'A']++; // 해당 인덱스의 값 1 증가
}
else { // 소문자 범위
arr[s.charAt(i) - 'a']++;
}
}
int max = -1;
char ch = '?';
for (int i = 0; i < 26; i++) {
if (arr[i] > max) {
max = arr[i];
ch = (char) (i + 65); // 대문자로 출력해야하므로 65를 더해준다.
}
else if (arr[i] == max) {
ch = '?';
}
}
System.out.print(ch);
}
}
package 백준배열;
import java.util.Scanner;
public class 크로아티아알파벳 {
public static void main(String[] args) {
Scanner sc=new Scanner(System.in);
String[] arr= {"c=", "c-", "dz=", "d-", "lj", "nj", "s=", "z=","e", "a", "k"};
String str=sc.next();
int cnt=0;
for(int i=0;i<arr.length;i++) {
if(str.contains(arr[i])) {
cnt+=1;}
if(str.contains("dz=")) {
cnt-=1;
}
}
System.out.println(cnt);
}
}
나의 코드
아래는 구글링해서 얻은 고수분의 해설!
이 알고리즘대로 작성해서 만들면 자바의 경우 다음과 같은 에러를 발견할 수 있을 것이다.
java.lang.StringIndexOutOfBoundsException
즉 인덱스 참조 범위를 벗어났다는 것이다. ( = 참조할 수 없는 범위 )
왜일까?
예로들어 이러한 문자를 받았다고 생각해보자.
aedzdz=ls=c
그림으로 보자면 다음과 같을 것이다.
한번 위의 알고리즘대로 하나씩 해보면 알 수 있을 것이다.
i 가 10 일 때 반복문을 생각해보자.
그럼 str.charAt(10) 을 통해 ch 에 저장되고 ( ch = 'c' )
c 라는 문자를 받았기 때문에 첫 번째 조건문을 실행시키게 된다.
그리고 여기서 문제가 발생한다.
if( str.charAt(i + 1) == '=' )
aedzdz=ls=c 이 문자열에서 마지막 c 다음의 문자는 존재 하지 않는다.
그런데 charAt() 을 통해 참조하려고 하니까 StringIndexOutOfBoundsException 이라는 에러를 뱉는 것이다.
해결방법은 무엇일까?
간단하다. 현재 i 의 값이 문자열 길이(str.length) 에서 -1 값보다 작을 경우에만 다음 조건문을 실행시키면 된다.
( dz= 를 검사할 때는 i 가 str.length - 2 보다 작아야한다. )
import java.util.Scanner;
public class Main {
public static void main(String[] args) {
Scanner in = new Scanner(System.in);
String str = in.nextLine();
int count = 0;
for (int i = 0; i < str.length(); i++) {
char ch = str.charAt(i);
if(ch == 'c') { // 만약 ch 가 c 라면?
if(i < str.length() - 1) {
if(str.charAt(i + 1) == '=') { //만약 ch 다음 문자가 '=' 이라면?
// i+1 까지가 하나의 문자이므로 다음 문자를 건너 뛰기 위해 1 증가
i++;
}
else if(str.charAt(i + 1) == '-') {
i++;
}
}
}
else if(ch == 'd') {
if(i < str.length() - 1) {
if(str.charAt(i + 1) == 'z') {
if(i < str.length() - 2) {
if(str.charAt(i + 2) == '=') { // dz= 일 경우
i += 2;
}
}
}
else if(str.charAt(i + 1) == '-') { // d- 일 경우
i++;
}
}
}
else if(ch == 'l') {
if(i < str.length() - 1) {
if(str.charAt(i + 1) == 'j') { // lj 일 경우
i++;
}
}
}
else if(ch == 'n') {
if(i < str.length() - 1) {
if(str.charAt(i + 1) == 'j') { // nj 일 경우
i++;
}
}
}
else if(ch == 's') {
if(i < str.length() - 1) {
if(str.charAt(i + 1) == '=') { // s= 일 경우
i++;
}
}
}
else if(ch == 'z') {
if(i < str.length() - 1) {
if(str.charAt(i + 1) == '=') { // z= 일 경우
i++;
}
}
}
count++;
}
System.out.println(count);
}
}
놓친 부분: 이 알고리즘도 머리 속에 생각을 했었는데, 이걸 다 언제 일일이 입력하지 귀찮아서 넘겼다.. 해볼걸
그리고 위에 복붙한 사진처럼 c 다음 들어올 단어가 없기에 if(i<str.length()-1)이 조건을 넣은 걸 체크 잘 해야할듯!