370 likes | 796 Views
9 장 다형성. Lab 9-1. 목차. 상속에 의한 다형성 직군 ( 직원 종류 ) 모양 그리기 정렬 & 검색 다형 정렬 Integer 리스트의 검색 & 정렬. 직원 종류. Commission 클래스를 추가한다 . Hourly 클래스를 상속받는다 . 2 개의 instance 변수 ( 상속받은 변수 제외 ) 총 판매액 저장 변수 (type: double) 직원의 수수료 (Commission) 비율 변수 (type : double, % 로 표현 )
E N D
9장 다형성 Lab 9-1
목차 • 상속에 의한 다형성 • 직군(직원 종류) • 모양 그리기 • 정렬 & 검색 • 다형 정렬 • Integer 리스트의 검색 & 정렬
직원 종류 • Commission 클래스를 추가한다. • Hourly 클래스를 상속받는다. • 2개의 instance 변수(상속받은 변수 제외) • 총 판매액 저장 변수(type: double) • 직원의 수수료(Commission) 비율 변수 (type : double, %로 표현) • 구성자는 6개의 매개변수를 가진다. • 5개 : Hourly의 변수 –부모의 구성자에서 처리 (name, address, phone number, social security number, hourly pay rate) • 1개 : 직원의 수수료 비율 변수
직원 종류(Cont.) • public void addSales (double totalSales) 추가 • 총 판매 변수에 매개변수로 받은 변수 더함. • pay 메소드 • 일한 시간으로 임금 계산(부모의 pay() 사용)한 후, 수수료를 계산한 임금을 더한다. • 총 판매액은 0으로 초기화. • toString 메소드 • 부모의 toString()을 호출하고, 총 판매를 추가한다.
직원 종류(Cont.) • Test해보자. • Staff 클래스를 수정한다. • 배열의 크기를 ‘8’로 늘린다. • 두 명의 Commissioned 직원을 staffList에 추가한다. • Commissioned 직원 1 - 시간당 보수 : $6.25, 수수료 비율 : 20% - 일한 시간 : 35시간, 총 판매 : $400 • Commissioned 직원 2 - 시간당 보수 : $9.75, 수수료 비율 : 15% - 일한 시간 : 40, 총 판매 : $950
직원 종류(Cont.) – Firm.java //************************************************************************ // Firm.java // // 상속 다형성을 살펴본다. //************************************************************************ public class Firm { //-------------------------------------------------------------------- // 스태프를 생성 //-------------------------------------------------------------------- public static void main(String[] args) { Staff personnel = new Staff(); personnel.payday(); } }
직원 종류(Cont.) – Staff.java //************************************************************************ // Staff.java // // 각 부서별 스태프를 표현한다. //************************************************************************ public class Staff { StaffMember[] staffList; //-------------------------------------------------------------------- // 스태프 리스트를 구성한다. //-------------------------------------------------------------------- public Staff() { staffList = new StaffMember[6]; staffList[0] = new Executive ("Sam", "123 Main Line", "555-0469", "123-45-6789", 2423.07); staffList[1] = new Employee ("Carla", "456 Off Line", "555-0101", "987-65-4321", 1246.15); staffList[2] = new Employee ("Woody", "789 Off Rocker", "555-0000", "010-20-3040", 1169.23); staffList[3] = new Hourly ("Diane", "678 Fifth Ave.", "555-0690", "958-47-3625", 10.55); staffList[4] = new Volunteer ("Norm", "978 Suds Blvd.", "555-8374"); staffList[5] = new Volunteer ("Cliff", "321 Duds Lane", "555-7282"); ((Executive)staffList[0]).awardBonus (500.00); ((Hourly)staffList[3]).addHours (40); }
직원 종류(Cont.) – Staff.java //-------------------------------------------------------------------- // 모든 스태프에게 월급 지급. //-------------------------------------------------------------------- public void payday() { double amount; for (int count = 0; count < staffList.length; count++) { System.out.println(staffList[count]); amount = staffList[count].pay(); if (amount == 0.0) System.out.println("Thanks!"); else System.out.println("Paid : " + amount); System.out.println("------------------------------------------"); } } }
직원 종류(Cont.) – StaffMember.java //************************************************************************ // StaffMember.java // // 스태프 표현. //************************************************************************ abstract public class StaffMember { protected String name; protected String address; protected String phone; //-------------------------------------------------------------------- // 스태프의 정보를 구성. //-------------------------------------------------------------------- public StaffMember (String eName, String eAddress, String ePhone) { name = eName; address = eAddress; phone = ePhone; }
직원 종류(Cont.) – StaffMember.java //-------------------------------------------------------------------- // 기본적인 정보를 반환. //-------------------------------------------------------------------- public String toString() { String result = "Name : " + name + "\n"; result += "Address : " + address + "\n"; result += "Phone : " + phone; return result; } //-------------------------------------------------------------------- // 상속받은 클래스를 반드시 pay()를 재정의해야 함. //-------------------------------------------------------------------- public abstract double pay(); }
직원 종류(Cont.) – Volunteer.java //************************************************************************ // Volunteer.java // // 스태프(지원자)를 표현. //************************************************************************ public class Volunteer extends StaffMember { //-------------------------------------------------------------------- // 지원자의 정보를 구성. //-------------------------------------------------------------------- public Volunteer (String eName, String eAddress, String ePhone) { super (eName, eAddress, ePhone); } //-------------------------------------------------------------------- // 보수(0)을 반환. //-------------------------------------------------------------------- public double pay() { return 0.0; } }
직원 종류(Cont.) – Employee.java //************************************************************************ // Employee.java // // 임금을 받는 보통 직원 표현. //************************************************************************ public class Employee extends StaffMember { protected String socialSecurityNumber; protected double payRate; //-------------------------------------------------------------------- // 직원 정보 구성. //-------------------------------------------------------------------- public Employee (String eName, String eAddress, String ePhone, String socSecNumber, double rate) { super (eName, eAddress, ePhone); socialSecurityNumber = socSecNumber; payRate = rate; }
직원 종류(Cont.) – Employee.java //-------------------------------------------------------------------- // 직원 정보를 반환. //-------------------------------------------------------------------- public String toString() { String result = super.toString(); result += "\nSocial Security Number : " + socialSecurityNumber; return result; } //-------------------------------------------------------------------- // employee의 pay rate(임금률)을 반환. //-------------------------------------------------------------------- public double pay() { return payRate; } }
직원 종류(Cont.) – Executive.java //************************************************************************ // Executive.java // // 보너스를 받는 임원직 표현. //************************************************************************ public class Executive extends Employee { private double bonus; //-------------------------------------------------------------------- // 임원직 정보 구성. //-------------------------------------------------------------------- public Executive (String eName, String eAddress, String ePhone, String socSecNumber, double rate) { super (eName, eAddress, ePhone, socSecNumber, rate); bonus = 0; }
직원 종류(Cont.) – Executive.java //-------------------------------------------------------------------- // 보너스를 수여. //-------------------------------------------------------------------- public void awardBonus (double execBonus) { bonus = execBonus; } //-------------------------------------------------------------------- // 보통직원의 임금과 보너스의 합을 반환. //-------------------------------------------------------------------- public double pay() { double payment = super.pay() + bonus; bonus = 0; return payment; } }
직원 종류(Cont.) – Hourly.java //************************************************************************ // Hourly.java // // 시간당 임금을 받는 직원 표현. //************************************************************************ public class Hourly extends Employee { private int hoursWorked; //-------------------------------------------------------------------- // 시간당 임금을 받는 직원의 정보 구성. //-------------------------------------------------------------------- public Hourly (String eName, String eAddress, String ePhone, String socSecNumber, double rate) { super (eName, eAddress, ePhone, socSecNumber, rate); hoursWorked = 0; } //-------------------------------------------------------------------- // 직원이 일한 시간 계산.(기존의 일한 시간 + 추가시간) //-------------------------------------------------------------------- public void addHours (int moreHours) { hoursWorked += moreHours; }
직원 종류(Cont.) – Hourly.java //-------------------------------------------------------------------- // 임금 반환. //-------------------------------------------------------------------- public double pay() { double payment = payRate * hoursWorked; hoursWorked = 0; return payment; } //-------------------------------------------------------------------- // 직원의 정보를 반환. //-------------------------------------------------------------------- public String toString() { String result = super.toString(); result += "\nCurrent hours : " + hoursWorked; return result; } }
모양 그리기 • 추상 클래스 Shape을 작성한다. • instance 변수 : shapeName (type: String) • 추상 메소드 : area() (return type : double) • toString() : Shape의 이름을 반환. • rectangle클래스와 cylinder클래스를 작성한다. • Shape을 상속받는다. • rectangle 클래스 • 변수 : 가로, 세로, 면적 • cylinder 클래스 • 변수 : 반지름, 높이, 면적(PI*radius²*height) • toString()은 Sphere클래스와 유사.
모양 그리기(Cont.) • Paint클래스의 amount()를 수정한다. • 정확한 페인트 양이 반환되도록 return문을 수정. • shape의 면적 / coverage • print문은 남겨둔다. • PaintThings클래스를 완성한다. • 세 모양의 객체를 초기화한다. • deck : 20 X 35의 사각형 • bigBall : 반지름 15인 구 • tank : 반지름 10, 높이 30인 원기둥 • 주석에 따라 코드를 완성하고 테스트한다.
모양 그리기(Cont.) – Sphere.java //************************************************************************ // Sphere.java // // 구 표현. //************************************************************************ public class Sphere extends Shape { private double radius; //-------------------------------------------------------------------- // 구성자 : 구를 구성. //-------------------------------------------------------------------- public Sphere (double r) { super("Sphere"); radius = r; }
모양 그리기(Cont.) – Sphere.java //-------------------------------------------------------------------- // 구의 표면적을 반환. //-------------------------------------------------------------------- public double area() { return 4*Math.PI*radius*radius; } //-------------------------------------------------------------------- // 구의 정보를 반환. //-------------------------------------------------------------------- public String toString() { return super.toString() + " of radius " + radius; } }
모양 그리기(Cont.) – Paint.java //************************************************************************ // Paint.java // // 페인트의 타입을 표현. //************************************************************************ public class Paint { // 1 gallon당 평방 피트 private double coverage; //-------------------------------------------------------------------- // 구성자 : paint 객체 구성. //-------------------------------------------------------------------- public Paint (double c) { coverage = c; } //-------------------------------------------------------------------- // 페인트의 양을 반환. //-------------------------------------------------------------------- public double amount (Shape s) { System.out.println("Computing amount for " + s); return 0.0; } }
모양 그리기(Cont.) – PaintThings.java //************************************************************************ // PaintThings.java // // 다양한 모양의 도형의 표면을 칠할때, 필요한 페인트의 양을 계산. //************************************************************************ import java.text.DecimalFormat; public class PaintThings { //-------------------------------------------------------------------- // 몇 개의 shape, Paint 객체 생성. // 각 shape을 칠할 때 필요한 페인트의 양을 출력. //-------------------------------------------------------------------- public static void main(String[] args) { final double COVERAGE = 350; Paint paint = new Paint(COVERAGE); Rectangle deck; Sphere bigBall; Cylinder tank;
모양 그리기(Cont.) – PaintThings.java double deckAmt, ballAmt, tankAmt; // 3개의 shape을 초기화. // 각 shape이 필요로 하는 페인트 양 계산. // 각 shape이 필요로 하는 페인트 양 출력 DecimalFormat fmt = new DecimalFormat ("0.#"); System.out.println("\nNumber of gallons of paint needed..."); System.out.println("Deck " + fmt.format(deckAmt)); System.out.println("Big Ball " + fmt.format(ballAmt)); System.out.println("Tank " + fmt.format(tankAmt)); } }
다형 정렬 • Numbers.java를 살펴본다. • 컴파일이 되지 않는 이유는? • 에러 메시지를 보고 고쳐보자. • Strings.java를 작성한다. • Numbers.java와 유사. • String 객체의 배열에 저장하고 정렬. • insertionSort 알고리즘을 수정한다. • 내림차순으로 정렬되도록 수정한다. • Numbers.java, Strings.java insertionSort를 사용하도록 수정한다.
다형 정렬(Cont.) • Salesperson.java를 완성한다. • compareTo()를 완성한다. • 총 판매량을 비교한다. • 다른 객체보다 판매량이 적으면 : return 음수 • 다른 객체보다 판매량이 많으면 : return 양수 • 판매량이 같은 경우 : 이름순(알파벳)으로 비교! (같은 경우는 없다!)
다형 정렬(Cont.) • Test해보자. • WeeklySales.java를 실행한다. • 판매량이 적은 순으로, 알파벳 역순으로 정렬이 될 것이다. 결과를 확인해보자.
다형 정렬(Cont.) – Sorting.java //************************************************************************ // Sorting.java // // 선택정렬과 삽입 정렬 알고리즘을 보여준다. //************************************************************************ public class Sorting { //-------------------------------------------------------------------- // 선택 정렬 알고리즘을 사용해 지정된 객체 배열을 정렬한다. //-------------------------------------------------------------------- public static void selectionSort (Comparable[] list) { int min; Comparable temp; for (int index = 0; index < list.length-1; index++) { min = index; for (int scan = index+1; scan < list.length; scan++) { if (list[scan].compareTo(list[min]) < 0) min = scan; }
다형 정렬(Cont.) – Sorting.java // 값들을 교환한다. temp = list[min]; list[min] = list[index]; list[index] = temp; } } //-------------------------------------------------------------------- // 삽입 정렬 알고리즘을 사용해 지정된 객체 배열을 정렬한다. //-------------------------------------------------------------------- public static void insertionSort(Comparable[] list) { for (int index = 1; index < list.length; index++) { Comparable key = list[index]; int position = index; // 큰 값을 오른쪽으로 이동한다. while (position > 0 && key.compareTo(list[position-1]) < 0) { list[position] = list[position-1]; position--; } list[position] = key; } } }
다형 정렬(Cont.) – Numbers.java //************************************************************************ // Numbers.java // // 정수 배열에서의 선택 정렬을 보여준다. //************************************************************************ import java.util.Scanner; public class Numbers { //-------------------------------------------------------------------- // 정수 배열을 구성하고, 정렬한 다음 출력한다. //-------------------------------------------------------------------- public static void main(String[] args) { int[] intList; int size; Scanner scan = new Scanner (System.in); System.out.println("\nHow many integers do you want to sort? "); size = scan.nextInt(); intList = new int[size];
다형 정렬(Cont.) – Numbers.java System.out.println("\nEnter the numbers..."); for (int i = 0; i < size; i++ ) intList[i] = scan.nextInt(); Sorting.selectionSort(intList); System.out.println("\nYour numbers in sorted order..."); for (int i = 0; i < size; i++) System.out.println(intList[i] + " "); System.out.println(); } }
다형 정렬(Cont.) – Salesperson.java //************************************************************************ // Salesperson.java // // 판매원을 표현 - 성, 이름, 총 판매량 //************************************************************************ public class Salesperson implements Comparable { private String firstName, lastName; private int totalSales; //-------------------------------------------------------------------- // 구성자 : 주어진 정보로 판매원 객체를 설정한다. //-------------------------------------------------------------------- public Salesperson (String first, String last, int sales) { firstName = first; lastName = last; totalSales = sales; }
다형 정렬(Cont.) – Salesperson.java //-------------------------------------------------------------------- // 판매원의 스트링 표현을 반환한다. //-------------------------------------------------------------------- public String toString() { return lastName + ", " + firstName + " : \t" + totalSales; } //-------------------------------------------------------------------- // 판매원의 이름이 같은지를 결정한다. //-------------------------------------------------------------------- public boolean equals (Object other) { return (lastName.equals(((Salesperson)other).getLastName()) && firstName.equals(((Salesperson)other).getFirstName())); } //-------------------------------------------------------------------- // 순서를 결정하기 위해 총판매량과 이름을 사용한다. //-------------------------------------------------------------------- public int compareTo(Object other) { int result; return result; }
다형 정렬(Cont.) – Salesperson.java //-------------------------------------------------------------------- // 이름 접근자 //-------------------------------------------------------------------- public String getFirstName() { return firstName; } //-------------------------------------------------------------------- // 성 접근자 //-------------------------------------------------------------------- public String getLastName() { return lastName; } //-------------------------------------------------------------------- // 총 판매량 접근자 //-------------------------------------------------------------------- public int getSales() { return totalSales; } }
다형 정렬(Cont.) – WeeklySales.java //************************************************************************ // WeeklySales.java // 판매량의 순으로 판매원을 정렬한다. (많은 사람 ... 적은 사람) //************************************************************************ public class WeeklySales { public static void main(String[] args) { Salesperson[] salesStaff = new Salesperson[10]; salesStaff[0] = new Salesperson("Jane", "Jones", 3000); salesStaff[1] = new Salesperson("Daffy", "Duck", 4935); salesStaff[2] = new Salesperson("James", "Jones", 3000); salesStaff[3] = new Salesperson("Dick", "Walter", 2800); salesStaff[4] = new Salesperson("Don", "Trump", 1570); salesStaff[5] = new Salesperson("Jane", "Black", 3000); salesStaff[6] = new Salesperson("Harry", "Taylor", 7300); salesStaff[7] = new Salesperson("Andy", "Adams", 5000); salesStaff[8] = new Salesperson("Jim", "Doe", 2850); salesStaff[9] = new Salesperson("Walt", "Smith", 3000); Sorting.insertionSort(salesStaff); System.out.println("\nRanking of Sales for the Week\n"); for (Salesperson s: salesStaff) System.out.println(s); } }
Integer 리스트의 정렬 & 검색 • IntegerListTest.java에 메소드를 추가한다. • void replaceFirst(int oldVal, int newVal) • list에 이미 있는 oldVal을 newVal로 바꾼다. • list에 oldVal가 없을 때, 아무 일도 일어나지 않는다. (에러 아님!) • oldVal이 많은 경우, 첫 번째 oldVal을 바꾼다. • 힌트 : search 메소드 사용. • void replaceAll(int oldVal, int newVal) • List에 있는 모든 oldVal을 newVal로 바꾼다. • list에 oldVal가 없을 때, 아무 일도 일어나지 않는다. (에러 아님!) • replaceFirst()와 유사.
Integer 리스트의 정렬 & 검색(Cont.) • void sortDecreasing() • list를 감소하는 순서로 정렬한다. • 선택정렬 알고리즘을 응용한다. • int binarySearchD(int target) • 가정 : 감소하는 순서로 정렬된 list에 ‘target’이 존재. • 이진 검색을 응용한다. • IntegerListTest.java를 수정한다. • 추가한 메소드를 test하기 위해 menu에 옵션을 추가한다.