객체지향 프로그램밍 실습
* 요구사항
• 평균학점 계산 방법 = (학점수×교과목 평점)의 합계/수강신청 총학점 수
• MVC패턴(Model-View-Controller) 기반으로 구현한다.
• 일급 컬렉션 사용
package org.example;
import org.junit.jupiter.api.DisplayName;
import org.junit.jupiter.api.Test;
import java.util.List;
import static org.assertj.core.api.Assertions.assertThat;
/**
* 요구사항
• 평균학점 계산 방법 = (학점수×교과목 평점)의 합계/수강신청 총학점 수
• MVC패턴(Model-View-Controller) 기반으로 구현한다.
• 일급 컬렉션 사용
*/
public class GradeCalculatorTest {
// 학점계산기 도메인 : 이수한 과목(객체지향프로그래밍, 자료구조, 중국어회화), 학점 계산기
// 객체지향프로그래밍, 자료구조, 중국어회화 --> 과목(코스) 클래스
// 이수한 과목을 전달하여 평균학점 계산 요청 ---> 학점 계산기 ----->(학점수*교과목 평점 ) 의 합계----> 과목(코스)
// ----> 수강신청 총학점 수 ----> 과목(코스)
@DisplayName("평균 학점을 계산한다.")
@Test
void calculateGradeTest() {
List<Course> courses = List.of(new Course("OOP", 3,"A+"),
new Course("자료구조",3,"A+"));
GradeCalculator gradeCalculator = new GradeCalculator(courses);
double gradeResult = gradeCalculator.calculateGrade();
assertThat(gradeResult).isEqualTo(4.5);
}
}
- 이 클래스는 GradeCalculatorTest 를 나타낸다 주어진 과목 목록에 대한 평균 학점 계산을 검증하는 역활을 한다.
@DisplayName("평균 학점을 계산한다.")
@Test
void calculateGradeTest() {
List<Course> courses = List.of(new Course("OOP", 3,"A+"),
new Course("자료구조",3,"A+"));
GradeCalculator gradeCalculator = new GradeCalculator(courses);
double gradeResult = gradeCalculator.calculateGrade();
assertThat(gradeResult).isEqualTo(4.5);
}
}
- List<Course> courses 는 두개의 과목을 포함하는 과목 목록을 생성한다 이 두 과목은 "OOP" 와 "자료구조" 이며
각각 3학점으로 "A+" 성적을 가지고 있다.
- GradeCalculator gradeCalculator = new GradeCalculator(courses) 은 GradeCalculator 객체를 생성하고 생성자를 통해 위에서 생성한 과목 목록을 전달한다.
- double gradeResult = gradeCalculator.calculateGrade() 는 gradeCalculator 객체를 사용하여 평균 학점을 계산하고 결과를 gradeResult 변수에 저장한다.
- assertThat(gradeResult).isEqualTo(4.5) 는 gradeResult 가 4.5와 일치하는지를 확인하는 AssertJ의 메서드 이다. 여기서 예상 결과값은 4.5로 설정되어 있으므로, 이 테스트는 학점 계산 결과가 예상과 일치하는지 확인한다.
GradeCalculator 클래스의 평균 학점 계산을 테스트하며 주어진 과목 목록과 예상 결과를 사용하여 결과를 검증한다 테스트가 통과하면 Gradecalculator 클래스가 요구사항에 따라 정확히 동작함을 확인할수있다.
package org.example;
import org.junit.jupiter.api.DisplayName;
import org.junit.jupiter.api.Test;
import static org.assertj.core.api.Assertions.assertThatCode;
public class CourseTest {
@DisplayName("과목을 생성한다.")
@Test
void createTest() {
assertThatCode(()-> new Course("OOP", 3, "A+"))
.doesNotThrowAnyException();
}
}
- 이 테스트는 Course 클래스의 생성자를 테스트 하고 생성자가 예외를 던지지 않아야 함을 검증한다.
- assertThatCode(() -> new Course("OOP", 3, "A+")) 는 특정 코드 블록을 검증하는 AssertJ의 메소드이다
여기서 course 클래스의 생성자를 호출하고 인수로 "OOP", 3, "A+"를 전달
- .doesNotThrowAnyException() 는 해당 코드 블록이 어떠한 예외도 던지지 않아야 함을 검증하는 메소드이다 따라서 new Course("OOP", 3 , "A+") 를 호출하면 이 생성자가 예외를 던지지 않아야 테스트가 통과한다.
이 코드는 Course 클래스의 생성자가 예외를 던지지 않는지 테스트 하는 간단한 테스트 케이스를 보여준다 예외가 발생하지 않으면 테스트가 성공하고, 예외가 발생하면 테스트가 실패한다. 이러한 테스트는 코드의 신뢰성을 검증하는 데 도움이 된다.
package org.example;
public class Course {
private final String subject; // 과목명
private final int credit; // 학점
private final String grade; //성적 ( A+ , A , B+ .....)
public Course(String subject, int credit, String grade) {
this.subject = subject;
this.credit = credit;
this.grade = grade;
}
public double multiplyCreditAndCourseGrade() {
return credit * getGradeToNumber() ;
}
public int getCredit() {
return credit;
}
public double getGradeToNumber() {
double grade = 0;
switch (this.grade) {
case "A+":
grade = 4.5;
break;
case "A":
grade = 4.0;
break;
case "B+":
grade = 3.5;
break;
case "B":
grade = 3.0;
break;
case "C+":
grade = 2.5;
break;
case "C":
grade = 2.0;
break;
}
return grade;
}
}
- Course 클래스는 과목명(subject) , 학점(credit) , 성적(grade) 를 나타내며
주요 메소드를 통해 학점과 성적을 곱하고 성적을 숫자로 변환한다.
private final String subject; // 과목명
private final int credit; // 학점
private final String grade; //성적 ( A+ , A , B+ .....)
- 위 코드의 subject , credit , grade 라는 세 가지 필드를 가지고 있다 .
public Course(String subject, int credit, String grade) {
this.subject = subject;
this.credit = credit;
this.grade = grade;
- Course 클래스의 생성자는 과목명, 학점 ,성적을 받아서 객체를 초기화한다 이것은 해당 과목의 정보를 저장하는 데 사용된다.
public double multiplyCreditAndCourseGrade() {
return credit * getGradeToNumber() ;
}
multiplyCreditAndCourseGrade 메소드는 학점 (credit) 과 성적 (grade) 를 곱한 값을 반환 한다 . 이를 통해 과목의 가중치 학점을 계산할 수 있다.
public double getGradeToNumber() {
double grade = 0;
switch (this.grade) {
case "A+":
grade = 4.5;
break;
case "A":
grade = 4.0;
break;
case "B+":
grade = 3.5;
break;
case "B":
grade = 3.0;
break;
case "C+":
grade = 2.5;
break;
case "C":
grade = 2.0;
break;
}
return grade;
- getGradeToNumber 메소드는 성적 문자열 (grade) 을 숫자로 변환 하는 메소드 이다 이 메소드는 switch 문을 사용하여 성적 문자열을 해당 숫자로 매핑하고 반환한다.
- Course 클래스는 과목 정보를 효과적으로 저장하고 처리하는데 사용할 수 있으며, 학점과 성적을 계산하는데 필요한 메소드를 제공한다.
package org.example;
import java.util.List;
public class GradeCalculator {
private final Courses courses;
public GradeCalculator(List<Course> courses) {
this.courses = new Courses(courses);
}
/**
* 요구사항
• 평균학점 계산 방법 = (학점수×교과목 평점)의 합계/수강신청 총학점 수
• MVC패턴(Model-View-Controller) 기반으로 구현한다.
• 일급 컬렉션 사용
*/
public double calculateGrade() {
// ( 학점수 * 교과목 평점 )의 합계
double totalMultipliedCreditAndCourseGrade = courses.multiplyCreditAndCourseGrade();
// 수강신청 총학점 수
int totalCompletedCredit = courses.calculateTotalCompletedCredit();
return totalMultipliedCreditAndCourseGrade / totalCompletedCredit ;
}
}
- GradeCalculator 클래스는 Courses 객체를 포함하며 이객체는 Course 객체의 목록을 갖고 초기화 한다.
- claculateGrade 메서드는 평균 학점을 계산하는 메서드이다
totalMultipliedCreditAndCourseGrade 메서드를 호출하여 학점수와 교과목 평점을 곱한 값을 저장한다.
- totalCompletedCredit 변수는 courses 객체의 calculateTotalCompletedCredit 메서드를 호출하여 수강신청한
총 학점 수를 저장한다
- 마지막으로 계산된 합계를 총 학점 수로 나누어 평균 학점을 반환한다
package org.example;
import java.util.List;
public class Courses {
private final List<Course> courses;
public Courses(List<Course> courses) {
this.courses = courses;
}
public double multiplyCreditAndCourseGrade() {
return courses.stream()
.mapToDouble(Course:: multiplyCreditAndCourseGrade)
.sum();
}
public int calculateTotalCompletedCredit() {
return courses.stream()
.mapToInt(Course::getCredit)
.sum();
}
}
이 클래스는 주어진 과목 목록 (List<Course> courses)을 처리하는 역활을 한다 Courses 클래스는 GradeCalculator 클래스에 사용되며 평균 학점을 계산하기 위한 여러 메소드를 제공한다 이클래스는 요구사항을 충족하기 위해 구현된것이다.
public class Courses {
private final List<Course> courses;
public Courses(List<Course> courses) {
this.courses = courses;
}
- Courses 클래스는 List<Course> courses 라는 과목 목록을 가지고 있으며 생성자를 통해 이 목록을 초기화 한다.
public double multiplyCreditAndCourseGrade() {
return courses.stream()
.mapToDouble(Course:: multiplyCreditAndCourseGrade)
.sum();
}
- multiplyCreditAndCourseGrade 메소드는 각 과목의 학점과 교과목 평점을 곱한 값의 합계를 반환한다.
- courses.stream() 은 과목 목록을 스트림으로 변환한다.
- mapToDouble(Course::multiplyCreditAndCourseGrade) 은 각 과목에 대해 multiplyCreditAndCourseGrade 메소드를 호출 하고 결과를 double로 매핑한다 결과를 double로 매핑한다.
- .sum() 은 이들 값을 합산하여 총계를 반환한다.
public int calculateTotalCompletedCredit() {
return courses.stream()
.mapToInt(Course::getCredit)
.sum();
}
}
- calculateTotalCompletedCredit 메소드는 과목 목록의 총 학점수를 계산하여 반환한다.
- courses.stream() 은 과목 목록을 스트림으로 변환한다.
- mapToInt(Courses::getCredit) 은 각 과목의 학점을 int로 매핑 한다.
- sum() 은 이들 값을 합산하여 총 학점 수를 반환한다.
스트림 변환을 하는 이유는
1. 함수형 프로그래밍 : 이터 처리를 보다 간결하게 표현할 수 있게 돕습니다. 스트림을 사용하면 데이터 조작에 필요한 중간 및 최종 연산을 체이닝하여 표현할 수 있다.
2. 편의성 : 스트림을 사용하면 데이터를 이터레이션(iteration)하거나 반복(iteration)하는 전통적인 방법에 비해 코드가 더 간결하고 읽기 쉽다.
3. 병렬 처리: 스트림을 사용하면 병렬 처리를 쉽게 구현할 수 있다. 데이터를 여러 코어에서 동시에 처리하면 성능을 향상시킬 수 있다.
4. 컬렉션과의 연동: 스트림은 기존의 컬렉션과 원활하게 연동하여 데이터를 처리할 수 있게 하고 컬렉션에서 스트림으로 변환하거나 스트림을 컬렉션으로 변환하는 것이 간단
따라서 courses를 스트림으로 변환함으로써 코드를 더 간결하게 작성하고 데이터 처리를 보다 효율적으로 수행할 수 있게 되며, 스트림을 활용하여 요구사항을 충족하는 데이터 처리를 쉽게 수행할 수 있다.
'JAVA > 객체지향' 카테고리의 다른 글
객체지향 프로그래밍 실습(3) (1) | 2023.10.31 |
---|---|
객체지향 프로그래밍(1) (1) | 2023.10.29 |
객체지향 개념정리 (1) | 2023.10.27 |
01. 테스트코드 (0) | 2023.10.26 |
포스팅이 좋았다면 "좋아요❤️" 또는 "구독👍🏻" 해주세요!