Collections Framework

|

배열은 연관된 데이터를 관리하기 위한 수단이었다. 그런데 배열에는 몇가지 불편한 점이 있었는데 그 중의 하나가 한번 정해진 배열의 크기를 변경할 수 없다는 점이다. 이러한 불편함을 컬렉션즈 프래임워크를 사용하면 줄어든다.

 

배열은 그 크기를 한번 지정하면 크기보다 많은 수의 값을 저장할 수 없다.

 

하지만 ArrayList는 크기를 미리 지정하지 않기 때문에 얼마든지 많은 수의 값을 저장할 수 있다.

 

ArrayList는 배열과는 사용방법이 조금 다르다. 배열의 경우 값의 개수를 구할 때 .length를 사용했지만 ArrayList는 메소드 size를 사용한다. 또한, 특정한 값을 가져올 때 배열은 [인덱스 번호]를 사용했지만 컬렉션은 .get(인덱스 번호)를 사용한다.

 

단, ArrayList를 사용하면 Object의 데이터 타입을 가지기 때문에, 제네릭을 사용해서 ArrayList 내에서 사용할 데이터 타입을 인스턴스를 생성할 때 지정할 수 있기 때문에 데이터를 꺼낼 때(String val = al.get(i);) 형변환을 하지 않아도 된다.

 

################ 컬렉션즈 프래임워크란? ################

컬렉션즈 프래임워크라는 것은 다른 말로는 컨테이너라고도 부른다. 즉 값을 담는 그릇이라는 의미이다. 그런데 그 값의 성격에 따라서 컨테이너의 성격이 조금씩 달라진다. 자바에서는 다양한 상황에서 사용할 수 있는 다양한 컨테이너를 제공하는데 이것을 컬렉션즈 프래임워크라고 부른다. ArrayList는 그중의 하나다.

List와 Set의 차이점은 List는 중복을 허용하고, Set은 허용하지 않는다.

 

################ Set ################

Set은 한국어로 집합이라는 뜻이다. 여기서의 집합이란 수학의 집합과 같은 의미다. 수학에서의 집합도 순서가 없고 중복되지 않는 특성이 있다는 것이 기억날 것이다. (기억나지 않아도 상관없다) 수학에서 집합은 교집합(intersect), 차집합(difference), 합집합(union)과 같은 연산을 할 수 있었다. Set도 마찬가지다.

 

public static void main(String[] args) {

HashSet<Integer> A = new HashSet<Integer>();

A.add(1);

A.add(2);

A.add(3);



HashSet<Integer> B = new HashSet<Integer>();

B.add(3);

B.add(4);

B.add(5);



HashSet<Integer> C = new HashSet<Integer>();

C.add(1);

C.add(2);

 

################ iterator ################

iterator에 담겨있는 값은 참조값이고, 오리지널값이 아니다!!!

인터페이스 iterator는 아래 3개의 메소드를 구현하도록 강제하고 있는데 각각의 역할은 아래와 같다.

  • hasNext
    반복할 데이터가 더 있으면 true, 더 이상 반복할 데이터가 없다면 false를 리턴한다.
  • next
    hasNext가 true라는 것은 next가 리턴할 데이터가 존재한다는 의미다. 

이러한 기능을 조합하면 for 문을 이용하는 것과 동일하게 데이터를 순차적으로 처리할 수 있다.

 

################ Map ################

 

Map 컬렉션은 key와 value의 쌍으로 값을 저장하는 컬렉션이다.

Map에서 데이터를 추가할 때 사용하는 API는 put이다. put의 첫번째 인자는 값의 key이고, 두번째 인자는 key에대한 값이다. key를 이용해서 값을 가져올 수 있다.

System.out.println(a.get("one"));

이것이 Map의 가장 기본적인 사용법이다. 그럼 Map에 저장된 데이터를 열거할 때는 어떻게 해야할까?

Set<Map.Entry<String, Integer>> entries = map.entrySet();

for (Map.Entry<String, Integer> entry : entries) {

System.out.println(entry.getKey() + " : " + entry.getValue());

}

메소드 entrySet은 Map의 데이터를 담고 있는 Set을 반환한다. 반환한 Set의 값이 사용할 데이터 타입은 Map.Entry이다. Map.Entry는 인터페이스인데 아래와 같은 API를 가지고 있다.

  • getKey
  • getValue

위의 API를 이용해서 Map의 key, value를 조회할 수 있다.

 

################ 정렬 ################

컬렉션을 사용하는 이유 중의 하나는 정렬과 같은 데이터와 관련된 작업을 하기 위해서다. 정렬하는 법을 알아보자. 패키지 java.util 내에는 Collections라는 클래스가 있다. 이 클래스를 사용하는 법을 알아보자.

 

package org.opentutorials.javatutorials.collection;

 

import java.util.*;

 

class Computer implements Comparable{

int serial;

String owner;

Computer(int serial, String owner){

this.serial = serial;

this.owner = owner;

}

public int compareTo(Object o) {

return this.serial - ((Computer)o).serial;

}

public String toString(){

return serial+" "+owner;

}

}

 

public class CollectionsDemo {

 

public static void main(String[] args) {

List<Computer> computers = new ArrayList<Computer>();

computers.add(new Computer(500, "egoing"));

computers.add(new Computer(200, "leezche"));

computers.add(new Computer(3233, "graphittie"));

Iterator i = computers.iterator();

System.out.println("before");

while(i.hasNext()){

System.out.println(i.next());

}

Collections.sort(computers);

System.out.println("\nafter");

i = computers.iterator();

while(i.hasNext()){

System.out.println(i.next());

}

}

 

}

결과

before

500 egoing

200 leezche

3233 graphittie

 

after

200 leezche

500 egoing

3233 graphittie

 

클래스 Collectors는 다양한 클래스 메소드를 가지고 있다. 메소드 sort는 그 중의 하나로 List의 정렬을 수행한다. 다음은 sort의 시그니처다.

 

public static <T extends Comparable<? super T>> void sort(List<T> list)

 

sort의 인자인 list는 데이터 타입이 List이다. 즉 메소드 sort는 List 형식의 컬렉션을 지원한다는 것을 알 수 있다. 인자 list의 제네릭 <T>는 coparable을 extends 하고 있어야 한다. Comparable은 인터페이스인데 이를 구현하고 있는 클래스는 아래 메소드를 가지고 있어야 한다.

아래의 메소드는 이러한 제약 조건을 준수하기 위해서 구현한 메소드다.

public int compareTo(Object o) {

return this.serial - ((Computer)o).serial;

}

메소드 sort를 실행하면 내부적으로 compareTo를 실행하고 그 결과에 따라서 객체의 선후 관계를 판별하게 된다.

이렇게 해서 컬렉션즈 프레임워크에 대한 수업을 마무리 하겠다. 컬렉션즈 프레임워크는 효율적인 에플리케이션을 구축하기 위해서 매우 중요한 내용이다. 그런데 컬렉션은 단순히 사용법을 이해하는 것으로는 부족하고, 소위 알고리즘이나 자료구조(data structure)라고 불리는 분야에 대한 충분한 이해가 필요하다. 컬렉션즈 프레임워크는 이러한 분야의 성취를 누구나 쉽게 사용할 수 있도록 제공되는 일종의 라이브러리라고 할 수 있기 때문이다.

'Java' 카테고리의 다른 글

은행계좌시스템  (0) 2019.07.01
문자열  (0) 2019.06.27
제네릭  (0) 2019.06.15
참조  (0) 2019.06.14
상수와 enum  (0) 2019.06.12
And