1. 수강관리 프로그램 메뉴 선택 구현
1) 조건
- 숫자만 입력하고 그 외 입력은 하지 않음
- Scanner 클래스의 nextInt 함수 이용
- 시작화면은 다음과 같이 구현(이미지 참고)
- 1 입력 후 엔터 -> "회원 관리 메뉴를 선택했습니다." 출력 후 다시 시작 화면으로
- 2 입력 후 엔터 -> "과목 관리 메뉴를 선택했습니다." 출력 후
- 3 입력 후 엔터 -> "수강 관리 메뉴를 선택했습니다." 출력 후 다시 시작 화면으로
- 4 입력 후 엔터 -> "결제 관리 메뉴를 선택했습니다." 출력 후 다시 시작 화면으로
- 5 입력 후 엔터 -> "프로그램을 종료합니다." 출력 후 프로그램 종료
- 그외 숫자 입력 후 엔터 -> "입력값이 정확하지 않습니다." 출력 후 다시 시작 화면으로
2) 코드
import java.util.Scanner;
public class JavaSurpriseTask01 {
public static void main(String[] args) {
// 1주차 자바 깜짝 과제-수강생 이소미
// 수강관리 프로그램 메뉴 선택
// 무한반복문(5를 누를 때까지 계속 메뉴 선택 가능)
while (true) {
System.out.println("<<<<[메뉴선택]>>>>");
System.out.println("1. 회원 관리");
System.out.println("2. 과목 관리");
System.out.println("3. 수강 관리");
System.out.println("4. 결제 관리");
System.out.println("5. 종료");
System.out.println();
System.out.println("1~5번 중 원하시는 메뉴의 숫자를 입력하세요 > ");
// 사용자에게서 숫자 입력받기
Scanner sc = new Scanner(System.in);
int menu = sc.nextInt();
// 5를 누르면 프로그램 종료
if (menu == 5) {
System.out.println("프로그램을 종료합니다.");
break;
} else {
switch (menu) {
// 1을 누르면 회원 관리 메뉴 선택
case 1:
System.out.println("회원 관리 메뉴를 선택했습니다.");
System.out.println();
break;
// 2를 누르면 과목 관리 메뉴 선택
case 2:
System.out.println("과목 관리 메뉴를 선택했습니다.");
System.out.println();
break;
// 3을 누르면 수강 관리 메뉴 선택
case 3:
System.out.println("수강 관리 메뉴를 선택했습니다.");
System.out.println();
break;
// 4를 누르면 결제 관리 메뉴 선택
case 4:
System.out.println("결제 관리 메뉴를 선택했습니다.");
System.out.println();
break;
// 1~5 외에 다른 숫자를 입력하면 출력되는 문구
default:
System.out.println("입력값이 정확하지 않습니다.");
System.out.println();
break;
}
}
}
}
}
3) 출력 결과
4) 회고
사실 최근에 이 코드와 비슷하게 야구 게임 프로그램을 구현해본 적이 있어서, 그 코드를 참고해서 쉽게 작성할 수 있었던 것 같다.
출력 결과 가독성을 위해 switch문에서 System.out.println();을 한번 더 하고 break를 넣었는데, 지금 생각해보니 윗줄의 System.out.println("[문자열]") 속에.. 문자열 뒤에 \n을 붙이면 되지 않나 싶다.... 다음엔 참고해야겠다.
그리고 다른 분 코드를 보니, 유지보수성을 생각하시고 메뉴 출력 부분과 프로그램 동작 부분을 메서드 여러 개로 따로 분리하신 분이 있더라... 멋졌다. 나도 분명 메서드를 배웠었는데... 다음엔 유지보수성도 고민해봐야겠다.
2. 대통령 취임사 알파벳 별 출현 빈도 구현
1) 조건
- 다음 글을 텍스트 파일에 넣어 문장의 각 영문 알파벳 별 출현 빈도의 개수를 구하고, 전체알파벳 중 몇 % 비율로 나오는지 구하기(이미지 참고)
- 전체 문자열의 길이는 String.length() 함수 사용
- 문자열(String)에서 특정 자리의 문자를 가져오는 String.charAt(index) 함수를 이용
- 영문 알파벳의 대소문자는 구분하지 않음
- 출력 형식을 아래 이미지처럼 맞추기
- 내용은 텍스트 파일에서 읽어오고, 파일에서 텍스트를 읽어오는 소스는 추가 클래스 참조
2) 코드
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.text.DecimalFormat;
import java.util.List;
// 1주차 자바 깜짝 과제 2번-수강생 이소미
// 대통령 취임사 알파벳 별 출현 빈도
// 파일 읽어오는 클래스 (제로베이스 제공)
class FileUtils {
public String getLoadText(String filePath) {
// 내부 버퍼를 사용하여 문자열을 저장하고 수정하는 클래스
StringBuilder sb = new StringBuilder();
try {
// 주어진 파일 경로에서 파일을 읽어옴
Path path = Paths.get(filePath);
// 파일의 모든 줄을 리스트로 읽어옴
List<String> lines = Files.readAllLines(path);
for (int i = 0; i < lines.size(); i++) {
if (i > 0) {
// 줄 사이에 개행 문자 추가(줄바꿈)
sb.append("\n");
}
// 각 줄을 StringBuilder에 추가
sb.append(lines.get(i));
}
} catch (IOException e) {
// 예외 발생 시 스택 트레이스 출력
e.printStackTrace();
}
// 파일 내용을 문자열로 반환
return sb.toString();
}
}
public class JavaSurpriseTask02 {
public static void main(String[] args) {
// FileUtils 클래스로 객체 생성
FileUtils file = new FileUtils();
// FileUtils 클래스 내부 메서드로 파일 내용 읽어오기
String filePath = file.getLoadText("C:/president_speech.txt/");
// 대소문자 구분 없이 세기 위해 모두 대문자로 변경
filePath = filePath.toUpperCase();
// 알파벳 빈도 저장을 위한 정수 배열 (A-Z, a-z)
int[] alphabets = new int[26];
// 전체 알파벳 수를 저장할 변수
int sum = 0;
// 파일 내용의 모든 문자 검사
for (int i = 0; i < filePath.length(); i++) {
// 현재 아스키코드 숫자에 맞는 알파벳 반환
char letter = (char) (filePath.charAt(i));
// 알파벳인 경우 카운팅
if (Character.isLetter(letter)) {
//'A'로부터 몇 번째인지 계산
alphabets[letter - 'A']++;
// 알파벳의 총 개수 증가
sum++;
}
}
// 각 알파벳의 빈도와 비율 출력
for (int i = 0; i <= filePath.length(); i++) {
// 각 아스키코드 숫자에 맞는 알파벳 반환
String letter = ((char) ('A' + i)) + "=";
// 소수점 둘째 자리까지 반올림하는 DecimalFormat 생성
DecimalFormat df = new DecimalFormat("#.##");
float percent = ((float) alphabets[i] / sum) * 100;
// 숫자를 문자열로 변환하고 공백을 추가하여 자릿수 맞추기
String countStr = String.format("%6d" + "개, ", alphabets[i]);
String percentStr = String.format("%8s", df.format(percent) + "%");
System.out.println(letter + countStr + percentStr);
}
}
}
3) 출력 결과
4) 회고
이 문제에서 여러모로 많이 헤맸던 것 같다.
일단 저 텍스트 파일을 따로 다운받아야 하는 건가 싶어서 구글링을 했는데 .txt 파일이 어디에도 없어서 멘붕이 왔다..
한참 뒤져보다가 지푸라기라도 잡는 심정으로 저 이미지의 글자를 드래그해봤는데 당연하게도 복사가능하게 되어 있었다... 민망했다. 메모장을 열고 내용에 복사 붙여넣기 해서 텍스트 파일을 만들 수 있었다.
출력하고 보니 예제 이미지랑 %부분만 달라서 좀 당황했는데, 확인해보니 저 %가 나오게 하려면 파일 전체를 다 읽어온 것을 세어 sum 변수에 담아야 했고 내 sum 변수의 값은 그것보다 1000정도 작았다.
근데 파일에서 알파벳만 전부 세는 거면 파일 전체보다 개수가 적어야 하는 게 당연하지 않나 싶어서 그냥 그대로 제출했다.. 마지막에 Exception이 발생하긴 했는데 원인을 모르겠고 내용은 전부 정상출력 되길래 패스했다...
문자열 포맷 부분에서 printf를 쓰지 않고 여러 개 변수에 출력할 내용들 전부 담은 후 변수명만 println()안에 담고 다른 문자열과 합쳐서 출력했는데, 이유는 단순하다. printf에 넣으면 필연적으로 코드가 가로 한 줄로 길어지게 되는데 나는 그게 가독성이 떨어진다고 느껴져서 거부감이 들기 때문이다(...)
소수 둘째 자리까지 표시하는 부분에서 Math.round 함수를 쓰지 않은 이유도 위와 같다. 코드가 가로 한 줄로 길어져 가독성이 떨어져 보인다. 그리고 MySQL에 더 익숙해서 그런지 Java의 round 함수에선 'round(실수,자릿수)' 형식이 안 되고 'round(실수)' 형식만 되기 때문에 100을 곱한 뒤 100을 나눠야 하는 게 너무 번거롭다...ㅠㅋㅋㅋㅋ
휴... 분명 파일 읽기는 다른 강의에서 배운 적이 있었는데, 제공받은 파일 클래스 코드가 잘 이해되지 않는 데다가 코드 추가를 어떻게 해야 할 지 감이 오질 않아 구글링과 Chat GPT의 힘을 많이 빌렸다...
내가 스스로 코드를 아예 고민해보지도 않은 건 아니지만 좀 부끄러웠다.
이런 훌륭한 도구들이 나올 만큼 문명이 많이 발달해서 다행이다...
'자바(JAVA) > 미니 프로젝트 & 기초 공부' 카테고리의 다른 글
Java 기초 다시 공부하기 4주차 - 달력 출력 프로그램, 가상 대선 당선 시뮬레이션 프로그램 (0) | 2024.06.30 |
---|---|
Java 기초 다시 공부하기 3주차-놀이동산 입장권 계산 프로그램 구현, 주민등록번호 생성 프로그램 구현 (1) | 2024.06.22 |
Java 기초 다시 공부하기 2주차-콘솔 화면에 구구단 1~9단 출력하기, 결제 금액 캐시백 계산 프로그램 구현 (0) | 2024.06.12 |
자바(JAVA) 미니 프로젝트-간단한 캘린더 프로그램 만들기 2 (5단계~7단계) (0) | 2022.03.30 |
자바(JAVA) 미니 프로젝트-간단한 캘린더 프로그램 만들기 (1~3 단계) (0) | 2022.03.22 |