자바의 정석 ch11-7~11 ArrayList

Luna·2023년 6월 8일
0

JAVA

목록 보기
20/32

ch11-7 ArrayList

  • ArrayList는 기존의 Vector를 개선 한 것으로 구현 원리와 기능적으로 동일
  • ArrayList와 달리 Vector는 자체적으로 동기화 처리가 되어있다.
    동기화는 13장 Thread에서 자세히 배우게 됨.
  • List 인터페이스를 구현하므로, 저장순서가 유지되고 중복을 허용한다.
  • 데이터의 저장 공간으로 배열을 사용한다. (배열기반)

ch11-8 ArrayList의 메서드

1. ArrayList()

  • 기본 생성자

2. ArrayList(Collection c)

  • 컬렉션들끼리 변환할 때 많이 사용한다.

3. ArrayList(int initialCapacity)

  • 배열의 길이를 넣어준다. 배열은 한 번 만들면 길이를 바꿀 수 없다.

4. 추가

  • boolean add(Object o) : 성공시 true, 실패 시 false 반환
  • void add(int index, Object element) : 저장 위치를 정해 줄 수 있다.
  • boolean addAll(Collection c)
  • boolean addAll(int index, Collection c)

5. 삭제

  • boolean remove(object o)
  • Object remove(int index) : 특정 위치에 있는 객체를 삭제
  • boolean removeAll(Collection c) : 컬렉션에 있는 객체를 삭제
  • void cleae() : 모든 객체를 삭제

6. 검색

  • int indexOf(Object o) : 객체가 몇 번째에 저장되어 있는지 찾음. 못 찾으면 -1을 반환. 배열 앞에서부터 찾음 (순방향)
  • int lastIndexOf(Object o) : 배열 뒤에서부터 찾음 (역방향)
  • boolean contains(Object o) : 지정된 객체가 있는지, 존재하는지 물어봄.
  • Object get(int index) : 특정 위치에 있는 객체 반환
  • Object set(int index, Object element) : 특정 위치에 있는 객체를 변경

7. 그 외

  • List subList(int fromIndex, int toIndex) : from~to 사이에 있는 객체를 일부 가져와서 새로운 List를 만든다.
  • Object[] toArray() :ArrayList의 객체 배열을 반환
  • Object[] toArray(Object[] a)
  • boolean isempty() : 비어있는지 확인
  • void trimToSize() : 빈 공간을 제거
  • int size : ArrayList의 저장된 객체의 갯수를 반환

실습

ArrayList

// 기본길이(용량, capacity)가 10인 ArrayList를 생성
ArrayList list1 = new ArrayList(10);
// ArrayList에는 객체만 저장 가능
// autoboxing에 의해 기본형이 참조형으로 자동 변환
list1.add(new Integer(5)); // 원래는 이렇게 써야 하지만
list1.add(5); // 이렇게 써도 자동으로 변환 된다.

subList()

ArrayList list1 = new Arraylist(10);
list1.add(5); // index[0]
list1.add(4); // index[1]
list1.add(2); // index[2]
list1.add(0); // index[3]
list1.add(1); // index[4]
list1.add(3); // index[5]
ArrayList list2 = new ArrayList(list1.subList(1,4));
  • index 1부터 4까지 잘라서 새로운 배열을 만드는 것인데 이런 경우 1<=x<4 여서 index[4]는 출력되지 않고 index[1],index[2],index[3]의 값만 출력 된다. 그래서 출력값은 [4, 2, 0]이 된다.
  • 읽기 전용이라 새로운 ArrayList로 만들어 줘야 바꿀 수 있다.
// ArrayList(Collection c)
ArrayList list2 = new ArrayList(list1.subList(1,4));

// 풀어쓰면 아래의 두 줄과 같다
List sub = list1.subList(1,4); // sub는 읽기만 가능 [4, 2, 0]
ArrayList list2 = new ArrayList(sub) // sub와 같은 내용의 ArrayList 생성

sort()

// list1과 list1를 정렬한다.
// Collection은 인터페이스, Collections는 유틸 클래스
Collections.sort(list1); // 출력값 [0, 1, 2, 3, 4, 5]
Collections.sort(list2); // 출력값 [0, 2, 4]

containsAll()

System.out.println(list1.containsAll(list2); // 출력값 : true
  • list1이 list2의 요소를 모두 포함하고 있는지 묻는 메서드

add()

list2.add("B"); // [0, 2, 4, B]
list2.add("C"); // [0, 2, 4, B, C]
// 인덱스 번호 (위치)를 지정한 후 값을 추가
list2.add(3, "A"); // [0, 2, 4, A, B, C]
print(list2); // 출력값 : [0, 2, 4, A, B, C]
  • 인덱스를 지정해 줄 경우 그 자리에 들어가고 뒤에 있는 것들은 순서가 밀린다. 그렇기 때문에 부담이 가는 작업이다.

set()

list2.set(3, "AA");
// index[3]에 있던 "A"를 "AA"로 변경
// 출력값 : [0, 2, 4, AA B, C]
  • 기존 값은 없어지고 새로 다른 값으로 대체한다.

indexOf()

// 기존 list1의 값 [0, 1, 2, 3, 4, 5]
list1.add(0, "1"); // 추가 하고 나서의 값 : [1, 0, 1, 2, 3, 4, 5]
// index[0]의 1은 문자열이고, indext[2]의 1은 숫자이다.

// indexOf()는 지정된 객체의 위치(인덱스)를 알려준다.
list1.indexof("1"); // 출력값 : 0
list1.indexof(1); // 출력값 : 2
// list1.indexof(new Integer(1)); 원래는 이렇게 써야함.

remove()

list1.remove(0); // 출력값 : [0, 1, 2, 3, 4, 5]
list1.remove(new Integer(1)); // 출력값 : [0, 1, 2, 3, 4, 5]
  • 중간 요소를 삭제 할 경우 빈자리를 채우려고 뒤에 있던 값들이 앞으로 한칸씩 당겨진다.
// 현재 list1의 배열이 [1, 0, 1, 2, 3, 4] 일 경우
list1.remove(1); // 인덱스가 1인 객체가 삭제 되므로 [1, 1, 2, 3, 4]가 된다.
list1.remove(new Integer(1)); // 이래야 숫자 1을 삭제 할 수 있다.
list1.remove("1"); // 이렇게 하면 문자열 1이 삭제된다.
  • 어떤 위치에 있는 어떤 객체를 삭제 할 것인지 잘 확인해서 remove를 사용해야 한다.

retainAll() , contains()

// list1 = [1, 0, 1, 2, 3, 4, 5] list2 = [0, 2, 4, AA, B, C]

// retainAll()
System.out.println(list1.retainAll(list2)); // 출력값 : true
System.out.println(list1); // 출력값 : [0, 2, 4]

// contains()
for(int i = list2.size()-1; i >= 0; i--) {
	if(list1.contains(list2.get(i)))
    	list2.remove(i);
}
System.out.println(list1,list2);
  • retainAll() list1에서 list2와 겹치는 부분만 남기고 나머지는 삭제.
    list1과 list2의 교집합을 구하는 것.
  • contains() for문 설명
    : list2.get(0) -> list2의 인덱스 0번째에 있는 값이 list1에도 있는지 묻는다.
    있으면 true를 반환하고 0번째 인덱스를 remove한다.
    -> for문이 끝나면 list1에 있는 list2의 요소들이 삭제된다.
    -> list2-list1 차집합이라고 보면 됨.

ch11-10 ArrayList에 저장된 객체의 삭제 과정

Chapter 9는 어디에.....?

  • [0, 1, 2, 3, 4]라는 배열이 있을 때 인덱스 2번의 객체를 삭제(remove)하게 되면 [0, 1, 3, 4, 5]가 된다.
  • 처음 배열의 사이즈는 5이다.
  1. 삭제할 데이터 아래의 데이터를 한 칸씩 위로 복사해서 삭제할 데이터를 덮는다.
    : 이 떄의 배열 size는 5이고 배열은 [0, 1, 3, 4, 4] 인 상태.
  2. 데이터가 모두 한 칸씩 이동했으므로 마지막 데이터는 null로 변경한다.
    : data[size-1] = null / size는 5, 배열은 [0, 1, 3, 4, null]
  3. 데이터가 삭제되어 데이터의 개수가 줄었으므로 size의 값을 감소 시킨다.
    : size--; / size는 4, 배열은 [0, 1, 3, 4]
  • 삽입은 반대로 하면 된다.
  • 만약에 맨 끝의 값인 4(인덱스 5번)을 삭제하게 되면 1번 과정인 복사하는 과정을 거칠 필요가 없으므로 부담이 적어진다. 되도록이면 1번 과정이 일어나지 않도록 하는게 좋다.
  • ArrayList에 저장된 첫 번째 객체부터 삭제하는 경우는 배열 복사가 발생해서 성능상 좋지도 않고 전부 지울 수 없다. 그러나 마지막 객체부터 삭제하는 경우 배열 복사가 발생하지 않아서 조금 더 빠른 작업이 가능하다.

ch11-11 Java API 소스보기

  • C:\Program Files\Java\jdk1.8.0_202\src.zip

0개의 댓글