자바

고급자바_1220-1

정재화니 2022. 12. 20. 12:51

리스트와 정렬에 대한 예시문제를 풀어보았습니다.

문제) 학번(int), 이름(String), 국어점수, 영어점수, 수학점수, 총점, 등수를 멤버로 갖는
 Student클래스를 만든다. 이 Student클래스의 생성자에는 학번, 이름, 국어점수, 영어점수, 수학점수만
 인수값으로 받아서 초기화 되도록 처리한다.  이 Student 객체는 List에 저장하여 관리한다.
 List에 저장된 데이터들을 학번의 오름차순으로 정렬할 수 있는 내부정렬 기준을 구현하고,
 총점의 역순으로 정렬하는데 총점이 같으면 이름의 오름차순으로 정렬이 되는 외부정렬 기준 클래스를
 작성하여 정렬된 결과를 출력하시오.  (단, 등수는 List에 전체데이터가 추가된 후에 구하도록 한다.)


Student 클래스

class Student implements Comparable<Student>{
	private int num;
	private String name;
	private int kor;
	private int eng;
	private int math;
	private int sum;
	private int rank;
	
	//생성자
	public Student(int num, String name, int kor, int eng, int math) {
		this.num = num;
		this.name = name;
		this.kor = kor;
		this.eng = eng;
		this.math = math;
		this.sum = kor+eng+math;
	}

+ Getter, Setter, toString까지 포함해서 작성합니다.

//학번의 오름차순 
	@Override
	public int compareTo(Student stu) {
//		if(this.num > stu.getNum()) {
//			return 1;
//		}else if(this.num < stu.getNum()) {
//			return -1;
//		}else {
//			return 0;
//		}
		return Integer.compare(this.num, stu.getNum());
	}

학번의 오름차순으로 작성하는데 두가지 방법을 사용해봤습니다.

반복문으로 하는 방법과 Wrapper클래스를 사용하는 방법입니다. 

학번순서로 정렬이 된 것을 알 수 있다.

총점을 역순으로 정렬하고 총점이 같으면 이름으로 오름정렬을 만들어 보겠습니다.

외부정렬

Collections.sort(stdList, new SortSumDesc());
		System.out.println("총점 역순, 같으면 이름 오름정렬후...");
		for(Student mem : stdList) {
			System.out.println(mem);
		}
		System.out.println("-----------------------------------------------------------");

출력을 하게 되면

결과가 나오는 것을 볼 수 있다.


Set에 대하여 공부해보자

지금까지 공부했던 List는 데이터의 순서(index)가 있으며 중복되는 데이터를 저장할 수 있는데

Set은 데이터의 순서(index)가 없고 중복되는 데이터를 저장할 수 없다.

HashSet hs1 = new HashSet(); // 객체 생성
		
		// 데이터 추가하기 ==> add()메서드를 사용한다.
		// 반환값 : 추가성공(true), 추가실패(false)
		hs1.add("DD");
		hs1.add("AA");
		hs1.add(2);
		hs1.add("CC");
		hs1.add("BB");
		hs1.add(1);
		hs1.add(3);
		
		System.out.println("set의 개수 : " + hs1.size());
		System.out.println("set 데이터 : " + hs1);

List와 동일하게 add()메서드를 통하여 저장한다. 결과값을 보면

List와 다르게 데이터의 저장순서가 저장한대로 들어가지 않은것을 알 수 있다.

 

중복되는 데이터를 저장해 보자

// Set에 중복되는 데이터를 추가하면 false를 반환하고 데이터는 추가되지 않는다.
		boolean isAdd = hs1.add("FF");
		System.out.println("중복되지 않을 때 : " + isAdd);
		System.out.println("set 데이터 : " + hs1);
		System.out.println();
		
		isAdd = hs1.add("CC");
		System.out.println("중복될 때 : " + isAdd);
		System.out.println("set 데이터 : " + hs1);
		System.out.println();

중복되지 않을때의 결과와 중복되는 데이터를 저장했을 경우의 결과를 보면

중복되지 않은 값을 때는 true를 반환하며 저장이 되고 중복되는 값은 false를 반환하며 저장되지 않는것을 알 수 있다.


Set의 데이터를 수정하려면 수정하는 메서드가 없기 때문에 해당 자료를 삭제하고 추가해야한다.

삭제하는 방법은 List와 동일하게 remove()와 clear()를 통하여 할 수 있다.

hs1.remove("FF");
		System.out.println("삭제후 set : " + hs1);
		hs1.add("EE");
		System.out.println("set 데이터 : " + hs1);
		System.out.println();
		
		hs1.clear();
		System.out.println("set 데이터 : " + hs1);
		System.out.println();

결과를 보자면

FF를 삭제하고  EE를 추가하여 수정한 것 처럼 보이고 clear()를 통하여 전부다 삭제된 것을 알 수 있다.

 


Set에는 데이터의 순서(index)가 없기 때문에 List처럼 index를 하나씩 불러 올 수 없다.

그래서 데이터를 하나씩 얻기 위해서는 Iterator형의 객체로 변환해야 한다.

변환하는 방법은

Iterator it = hs1.iterator();	// Set데이터를 Iterator로 변환하기

		while(it.hasNext()) {
			System.out.println(it.next());
		}

hasNext()를 이용하여 다음번째에 데이터가 있는지 확인하고

next()를 이용하여 포인터를 다음번째 위치로 이동시키고 이동한 곳의 데이터를 반환한다.

Iterator말고 향상된 for문을 이용 할 수 있는데

System.out.println("향상된 for문 이용하기...");
		for(Object obj : hs1) {
			System.out.println(obj);
		}
		System.out.println("----------------------------------------------");

결과를 보면....

동일한 결과가 나오는 것을 알 수 있다.


예시를 통하여 알아보도록 하겠습니다.

예) 우리반 학생들 중 번호를 이용하여 추첨하는 프로그램을 작성해보자.
   번호는 1번부터 25번까지 있고 추첨할 인원은 3명이다. 당첨번호를 출력하시오.
 

Random rnd = new Random();
		HashSet<Integer> testSet = new HashSet<Integer>();
		while(testSet.size() < 3) {
			testSet.add(rnd.nextInt(25) + 1);
		}
		System.out.println("당첨자 번호 : " + testSet);

랜덤을 이용하여 난수를 받아서 당첨자 번호를 뽑아봅니다.

중복되지 않는 3개의 번호가 나오는 것을 알 수 있습니다.