[ITWILL : JAVA]배열과 함께쓰는 메서드

ITWILL학원 : 10강 JAVA BY 윤미영강사

1. for each문

향상된 for문인 for each문은 기존 for문과 비교해서 초기값과 증감식을 사용하지 않으며 배열이 가지고 있는 요소들을 특정 변수로 바로 할당해서 사용할 수 있게한다

1
2
3
for(데이터타입 변수명 : 반복할 배열명/컬렉션){
//반복할 문장
}

이 반복문은 내부적으로 배열의 인덱스 0번부터 배열의 길이만큼을 반복한다.

  • 장점 : 전체적으로 for문을 훨씬 간결히 작성할 수 있다.

  • 단점

    • 인덱스를 사용하지않고 사용불가능.
    • 반복 처리할 범위를 지정불가능.
  • 결론 : 따라서 인덱스를 써야하거나 특정범위를 반복해야하는 경우는 전통적인 for문을 쓰고 아닐 경우 for each를 쓰면 된다

아래 for문과 for each문의 예시를 보자.
랜덤한 짝수를 3개를 뽑은 뒤 그 합을 구해보자.

랜덤한 짝수 3개뽑기는 index를 사용해야하기때문에 for each를 쓸 수 없다.
뽑은 짝수합을 구하는 경우 index도 필요없고 특정범위반복도 필요없기때문에 for each를 쓰면 한결 간결해진다.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
int[] evendatas = new int[3];

//랜덤한 짝수 3개 뽑기
for(int i=0;i<evendatas.length;i++){
evendatas[i] = rd.nextInt(8)+1;
if(evendatas[i]%2 !=0){
evendatas[i] = evendatas[i]+1;
}
System.out.print(evendatas[i]+"\t");
}

//뽑은 짝수합구하기
evenSum = 0;
for(int data : evendatas){
evenSum+=data;
}
System.out.print("랜덤한 짝수의 합 : "+evenSum);

2. 배열 데이터의 정렬

배열과 같은 자료구조에 대해서는 정렬에 대한 요구사항이 빈번하다.
정렬을 구현하기 위한 알고리즘은 버블 정렬, 선택 정렬, 삽입 정렬 등 여러가지 방식이 있다.

Arrays.sort() 오름차순정렬

Arrays클래스 API를 이용하기 위해 import java.util.Arrays;해줘야한다.
만약 문자열을 관리하는 배열이 파라미터로 들어온다면 대문자->소문자의 사전순으로 정렬한다.

1
2
3
4
5
6
7
8
9
10
int[] data = {5, 7, 2, 9, 1};
Arrays.sort(data);

//정렬 후 출력
for(int x : data){
System.out.print(x + "\t");
}

//출력값
1 2 5 7 9

3. 배열 데이터의 출력 : Arrays.toString(arr)

배열데이터를 출력하기 위해서 for문을 이용해도 되지만 Arrays클래스 API를 이용하여 출력할수있다.
Arrays.toString(arr)사용하기 위해서는 import를 먼저 해야한다.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
String [] arr1 = {"JAVA", "is", "Not", "bad"};
Arrays.sort(arr1);

//배열출력1 : for each이용
for(String s :arr1){
System.out.print(s + "\t");
}
//배열출력2 : Arrays클래스 API이용
System.out.println(Arrays.toString(arr1));


// 출력값
JAVA Not bad is
[JAVA, Not, bad, is]

4. Arrays 로또 만들기

배열에 무작위 숫자로 구성된 로또를 만들고 정렬 후 출력하는 게임을 만들어보자.
로또는 1~45사이의 숫자로 구성되며 6개의 숫자를 랜덤으로 뽑느다.
그리고 모든 숫자의 중복 x.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
int[] selected = new int[6]; //로또를 저장할 배열
int[] fullBall = new int[45]; //모든 공의 정보를 가지고 있는 배열

int cnt= 0;
Random rd = new Random();
while(cnt < 6){ //총 6개의 공을 선택할 조건
int index = rd.nextInt(45); //0~44사이의 정수
int ball = fullBall[index];
if(ball ==0){ //중복체크
selected[cnt] = index +1;
fullBall[index] = -1;
cnt ++;
}
}
Arrays.sort(selected);
System.out.println(Arrays.toString(selected));
}
  1. random.nextInt(n)
    이는 0~(n-1)개의 정수를 랜덤하게 생성한다.
    그렇다면 여기선 random.nextInt(45)이므로 0~44사이의 랜덤한 정수를 생성하게된다.
    왜그럴까?
    selected된 공은 index에서 +1해주기때문이다
    if문을 보자.
    랜덤으로 index가 0이 걸리면 선택된 공은 1이되고
    랜덤으로 index가 44가 걸리면 선택된공은 45가된다.

  2. ball if문으로 중복체크
    ball = 0이 참이면 이 fullBall[index]가 한번도 뽑힌적이 없는 숫자라는 의미이다.
    그리고 선택되어지고 selected[cnt] = index +1을 준다.
    그리고 이미 뽑힌 수는 -1로 값을 준다.
    그렇게되면 다음번에 또 뽑혔을때 -1이기때문에 거짓이 되어 selected가 되지않는다.

1
2
3
예를 들어
fullBall[2]가 처음뽑혔으면 if문이 참이므로 selected[1]가 되고 로또숫자는 3이다.
그리고 난 뒤 fullBall[2] = -1로 바뀌어서 다음번에 뽑혀도 if문에서 거짓으로 팅겨나간다

5. System.arraycopy()

배열은 한 번 생성되면 메모리의 연속성때문에 그 크기를 변경할 수 없다.
하지먼 프로그래밍을 하다 보면 처음 예상했던 데이터의 개수보다 더 많은 데이터를 관리해야할 경우가 있다.
이를 예방하기위해 처음부터 배열의 크기를 크게 지정해버린다면 불필요한 메모리를 낭비하는 꼴이다.

필요에 따라 배열의 길이를 늘이기 위해서는 기존배열의 길이를 늘일수는 없고
배열의 길이 큰 새로운 배열은 만들고 기존 데이터를 복사해 넣은 다음 새로운 데이터를 추가해야한다.

첫번째 방법 : for문과 Arrays.toString()이용

1
2
3
4
5
6
7
8
9
int[] source = {1,2,3};
int[] newSource = new int[7]; //원하는 배열길이만큼의 숫자입력

for(int i=0; i<source.length; i++){
newSource[i] = source[i];
}System.out.println(Arrays.toString(newSource));

//출력값
[1, 2, 3, 0, 0]

두번째 방법 : System.arraycopy()와 Arrays.toString()이용

System.arraycopy(기존배열명, 카피할데이터인덱스, 새로운배열명, 데이터붙여넣을시작인덱스, source.length);

아래처럼 데이터붙여넣을시작인덱스에 2를 넣었기때문에 출력값은 인덱스2번부터 [0, 0, 1, 2, 3, 0, 0]부터 붙여넣기가 된다.
만약 0을 넣었다면 출력값은 인덱스0번부터 [1, 2, 3, 0, 0, 0, 0]이 된다.

1
2
3
4
5
6
7
int[] source = {1,2,3};
int[] newnewSource2 = new int[7] //원하는 배열길이만큼의 숫자입력
System.arraycopy(source, 0, newnewSource2, 2, source.length);
System.out.println(Arrays.toString(newnewSource2));

//출력값
[0, 0, 1, 2, 3, 0, 0]

5. Integer.parseInt(파라미터)

GUI환경에서 가장 잘 사용하는 메서드이다.
정수의 형태인 파라미터를 int로 변경해 리턴한다.
만약 파라미터가 정수형태가 아닐 경우 NumberFormatException 에러가 난다.