Java/JAVA 100 문제 풀이

자바 part.5 문제풀이 - 투표 시스템 만들기: 후보자의 투표 수 집계 및 과반수 판별

진이최고다 2023. 7. 30. 23:05

투표 시스템 만들기: 후보자의 투표 수 집계 및 과반수 판별

예제
class Solution{
	
	Solution(){}
	//Method
	public void solutionMethod(int n, int[]vote_box) {
		
		//[1] : 카운트(득표 수) 배열 선언 -> 정수형 배열은 0으로 초기화가 되어진다는 점을 활용 -> 즉, 처음에는 후보자 모두  0이라는 초기값을 가진다. 
		//이때, 후보자 0번 후보는 없으니까, 후보자 수 보다 1 많게 배열의 크기를 만든다. 
		int[] ar = new int[n+1];
	
		//[2] : 전달된 vote_box 배열을 반복문을 돌면서 각 후보자별로 표를 받는 득표 수 계산
		//결과적으로 ar배열에는 득표한 수가 저장.
		//여기가 이 문제에서 가장 중요한 핵심 포인트
		for(int i = 0; i < vote_box.length; i++) {
			ar[vote_box[i]]++;
		}
		
		//[3] : 각 후보자 득표 수 출력
		for(int i = 1; i < ar.length; i++) {
			System.out.println(i + "번 후보 총" + ar[i] + "표");
		}
		
		//[4] : ar카운트 배열에서 가장 많은 득표 수와 최다 득표 후보자 번호 출력 -> 최대값 알고리즘
		//먼저 max 변수에 0 또는 ar배열에 첫 번째 값을 셋팅하고, 반복문을 돌면서 각 요소와 max값을 비교하면서 더 큰 값을 저장.
		//이때, 0번 후보자인 배열 0번은 항상 0값이므로, 1부터 순회.
		int rst_candidate = 0, rst_max = ar[0];
		for(int i = 1; i < ar.length; i++) {
			if(ar[i] > rst_max) {
				rst_max = ar[i];
				rst_candidate = i;
			}
		}
		System.out.println("가장 많은 득표 수 -> " + rst_max + "표 이고, 후보자는  " + rst_candidate + "번 후보자 입니다.");
		
		//[5] : 과반 수 여부 체크
		boolean majority = rst_max > (vote_box.length / (double)2);
		if(majority) {
			System.out.println("과반수 이상 득표했습니다. -> 당선");
		}else {
			System.out.println("과반수 이상 실패했습니다. -> 미당선");
		}
	}
	
}

public class License_SolutionVote {
	
    public static void main(String[] args) {
    	
    	//[1]:객체 생성
    	Solution s1 = new Solution();
    	
    	//[2]:득표한 표 수를 저장하는 정수형 배열 선언
    	int[] vote_box = {1, 3, 1, 3, 3, 2, 3, 3};
    	
    	//[3]:SolutionMethod() 호출 -> 2개 입력 파라미터 값 전달 -> 후보자 수, 득표 수 배열
    	s1.solutionMethod(3, vote_box);
    }
}
1번 후보 총2표
2번 후보 총1표
3번 후보 총5표
가장 많은 득표 수 -> 5표 이고, 후보자는  3번 후보자 입니다.
과반수 이상 득표했습니다. -> 당선

이 코드는 투표 시스템으로, 가장 많은 표를 얻은 후보를 선출하고, 그 후보가 과반수의 표를 얻었는지를 확인한다. 


1. 초기화

Solution s1 = new Solution();
int[] vote_box = {1, 3, 1, 3, 3, 2, 3};

"Licens_SolutionVote" 클래스의 main 메서드에서 "Solution" 클래스가 인스턴스화 된다. 배열 "vote_box"는 투표를 저장하기 위해 정의하고, "vote_box" 배열의 각 요소는 특정 후보에 대한 투표박스에 해당한다. 후보들은 1부터 시작하는 정수 표시된다.

 

2. 투표집계

int[] ar = new int[n+1];
for(int i = 0; i < vote_box.length; i++) {
    ar[vote_box[i]]++;
}

"solutionMethod"에서는 각 후보가 받은 표의 수를 세기 위해 배열 "ar"가 생성된다. "ar"의 각 인덱스는 후보 번호에 해당하며, 해당 후보에게 투표할 때마다 그 값이 증가하기에, "vote_box" 배열을 순회하며 각 요소를 인덱스로 사용하여 "ar"의 해당 값을 증가시킨다.

 

3. 각 후보의 표수 표시

for(int i = 1; i < ar.length; i++) {
    System.out.println(i + "번 후보 총" + ar[i] + "표");
}

그 다음 "ar"를 순회하여 각 후보가 받은 표의 수를 출력한다. 후보 0이 존재하지않으므로, 인덱스는 0부터 시작한다.

 

4. 승자 결정

int rst_candidate = 0, rst_max = ar[0];
for(int i = 1; i < ar.length; i++) {
    if(ar[i] > rst_max) {
        rst_max = ar[i];
        rst_candidate = i;
    }
}
System.out.println("가장 많은 득표 수 -> " + rst_max + "표 이고, 후보자는  " + rst_candidate + "번 후보자 입니다.");

프로그램은 "ar"를 다시 순회하여 가장 많은 표를 얻은 후보를 찾는다. 가장 많은 표를 받은 후보와 그 표의 수를 추적하기 위해 "rst_max" 와 "rst_candate" 두 변수를 사용한다.

 

5. 과반수 확인

boolean majority = rst_max > (vote_box.length / (double)2);
if(majority) {
    System.out.println("과반수 이상 득표했습니다. -> 당선");
}else {
    System.out.println("과반수 이상 실패했습니다. -> 미당선");
}

그 다음 가장 많은 표를 얻은 후보가 총 표수의 과반수를 받았는지 확인한다. 이는 "vote_box.length"의 절반과 "rst_max"를 비교하여 이루어진다. "vote_box.length"를 2로 나누기 전에 "double"로 형변환하여 부동소수점 나눗셈의 정확성을 보장하고, 그 후에 "rst_max"와 비교한다.


import java.util.Arrays, java.util.OptionalInt 이용한 득표 수 최소값, 최대값 구하기

Arrays.sort(ar);
OptionalInt min = Arrays.stream(ar, 1, n+1).min();
System.out.println("가장 적은 득표 수(최소값)은 = " + min.getAsInt());
System.out.println("가장 많은 득표 수(최대값)은 = " + ar[ar.length-1]);
int rst_max = ar[ar.length-1];

Arrays 클래스의 sort 메서드는 전체 배열을 오름차순으로 정렬하기 때문에, ar[0]에는 사용하지 않는 값(0번 후보자의 득표 수)이 저장도므로, 최소 득표 수를 얻으려면 ar[1]부터 ar[n]까지의 값 중 가장 작은 값을 찾아야한다.

 

위 코드에서 "Arrays.stream(ar, 1, n+1)"는 ar[1]부터 ar[n]까지의 값으로 구성된 스트림을 생성한다. 그 후, "min()"메서드로 최소값을 찾아 "OptionalInt"에 저장한다. 

 

"OptionalInt"는 값을 포함하거나 포함하지 않을 수 있는 컨테이너 클래스이다. 이후 "getAsInt()"메서드로 값을 가져온다.