컬렉션 프레임워크란?
컬렉션
사전적 의미로 요소(객체)를 수집해서 저장하는 것
배열의 문제점
저장할 수 있는 객체 수가 배열으 생성할 때 결정
불특정 다수의 객체를 저장하기 위해서는 문제점이 많다
객체가 삭제했을 떄 해당 인덱스가 비게됨
List 컬렉션
득징
순서유지, 중복허용
인덱스로 관리
중복해서 객체 저장가능
구현클래스
ArrayList
Vector, Steck (Steck은 Vector의 자손)
LinkedList
Array List
데이터 저장공간을 배열을 사용한다.
객체제거 - 바로 뒤 인덱스부터 마지막 인덱스까지 모두 앞으로 1씩 당겨진다.
ArrayList에 저장된 객체의 삭제
list.remove(2)
전체 삭제는 뒤에서부터 삭제해야 삭제가 된다.
ArrayList 예제
package kr.co.kihd.arraylist;
import java.util.ArrayList;
public class ArrayListTest {
public static void main(String[] args) {
//ArrayList는 제네릭 타입이다.
//기본적으로 10개의 공간을 생성함.
ArrayList list = new ArrayList();
//저장된 객체가 하나도 없기 때문에 0을 리턴함.
System.out.println("총 크기 " + list.size());
list.add("111"); //boolean add(Object o) -> 순차적 추가
list.add("222");
list.add("333");
list.add("444");
System.out.println("총 크기 " + list.size());
list.add(333); //list.add(new Integer(333)); Auto boxing
System.out.println("총 크기 " + list.size());
System.out.println("ArrayList에 있는 값 : " + list.toString());
//0번째 인덱스에 "333"을 추가하기
list.add(0, "333");
System.out.println("ArrayList에 있는 값 : " + list.toString());
//앞에서부터 검색하여 "333"을 삭제한다.(가까운것 한개만 선택)
//객체 삭제하기
list.remove("333");
System.out.println("ArrayList에 있는 값 : " + list.toString());
System.out.println(list.remove("333"));
System.out.println("ArrayList에 있는 값 : " + list.toString());
//저장된 객체의 인덱스를 찾아오기(없으면 -1 리턴한다.)
System.out.println("index = " + list.indexOf("333"));
System.out.println("index = " + list.indexOf(333));
//객체를 전부 삭제하기
// list.clear();
// System.out.println("ArrayList에 있는 값 : " + list.toString());
//인덱스 0을 삭제할때, i가 0이니까 당연히 0인덱스에 있는 객체는 삭제되지만,
//이후 i값이 증가되면서 제대로 삭제가 되지 않는다.
//삭제시키려면 항상 뒤에서부터 삭제해야 한다.
// for(int i = 0; i<list.size(); i++) {
// list.remove(i);
// }
// System.out.println("ArrayList에 있는 값 : " + list.toString());
//아래와 같이 삭제를 하면 IndexOutOfBoundsException 이 발생한다.
//이유는 size()값이 4인데, 인덱스는 3가지 있으니 그렇다.
for(int i = list.size()-1; i>=0; i--) {
list.remove(i);
}
System.out.println("ArrayList에 있는 값 : " + list.toString());
}
}
package kr.co.kihd.arraylist;
import java.util.ArrayList;
import java.util.Collections;
public class ArrayListTest02 {
//출력하는 메서드 작성
public static void print(ArrayList<Integer> list1, ArrayList<Integer> list2) {
System.out.println("list1 : " + list1.toString());
System.out.println("list2 : " + list2.toString());
System.out.println();
}
public static void main(String[] args) {
ArrayList<Integer> list1 = new ArrayList();
list1.add(5); //자동박싱
list1.add(4);
list1.add(2);
list1.add(0);
list1.add(1);
list1.add(3);
//sublist()는 마지막 인덱스를 포함하지 않고 List타입으로 리턴함.
ArrayList list2 = new ArrayList(list1.subList(1, 4));
print(list1, list2);
//정렬하기
System.out.println("정렬 후");
Collections.sort(list1); //기본적으로 오름차순 정렬이다.
Collections.sort(list2);
print(list1, list2);
//포함관계
System.out.println("list1컬렉션 list2컬렉션의 모든 요소가 들어있느냐?");
System.out.println(list1.containsAll(list2));
System.out.println();
//추가하기
list2.add("B"); //배열 복사가 일어나지 않음.
list2.add("C"); //배열 복사가 일어나지 않음.
print(list1, list2);
list2.add(3,"A");
print(list1, list2); //배열 복사가 일어남
//대체하기
list2.set(3, "AA");
print(list1, list2);
//list2에서 list1에 포함된 객체들을 삭제하기
System.out.println("포함된 객체 삭제하기");
for(int i = list2.size()-1; i>=0; i--) {
if(list1.contains(list2.get(i))) {
list2.remove(i);
}
print(list1, list2);
}
}
}
List 컬렉션
vector 예제
package kr.co.kihd.vector;
public class Board {
String subject;
String content;
String writer;
public Board(String subject, String content, String writer) {
this.subject = subject;
this.content = content;
this.writer = writer;
}
}
package kr.co.kihd.vector;
import java.util.Iterator;
import java.util.Vector;
public class VectorTest {
public static void main(String[] args) {
//용량이 5인 백터를 생성한다.
Vector<Board> vector = new Vector<>(5);
System.out.println("용량 : " + vector.capacity());
System.out.println("초기 사이즈 : " + vector.size());
System.out.println("------------------------");
//객체추가
vector.add(new Board("제목1", "내용1", "글쓴이1"));
vector.add(new Board("제목2", "내용2", "글쓴이2"));
vector.add(new Board("제목3", "내용3", "글쓴이3"));
vector.add(new Board("제목4", "내용4", "글쓴이4"));
vector.add(new Board("제목5", "내용5", "글쓴이5"));
System.out.println("객체 추가 후 용량 : " + vector.capacity());
System.out.println("객체 추가 후 사이즈 : " + vector.size());
System.out.println("------------------------");
//객체 삭제
vector.remove(2); //배열복사
vector.remove(3); //배열복사
System.out.println("객체 삭제 후 용량 : " + vector.capacity());
System.out.println("객체 삭제 후 사이즈 : " + vector.size());
System.out.println("------------------------");
//용량만 확보
vector.ensureCapacity(20);
System.out.println("용량 확보 후 용량 : " + vector.capacity());
System.out.println("용량 확보 후 사이즈 : " + vector.size());
System.out.println("------------------------");
//null값 포함햐여 size값 변경
vector.setSize(7); //배열복사
System.out.println("size값 변경 후 용량 : " + vector.capacity());
System.out.println("size값 변경 후 사이즈 : " + vector.size());
System.out.println("------------------------");
//size로 잡히지 않은 null값은 삭제를 해준다.
vector.trimToSize();
System.out.println("null값 삭제 후 용량 : " + vector.capacity());
System.out.println("null값 삭제 후 사이즈 : " + vector.size());
System.out.println("------------------------");
vector.setSize(3);
System.out.println("size값 변경 후 용량 : " + vector.capacity());
System.out.println("size값 변경 후 사이즈 : " + vector.size());
System.out.println("------------------------");
for(Board board : vector) {
System.out.println(board.subject + board.content + board.writer);
}
System.out.println("------------------------");
//반복자(iterator) 로 출력하기
Iterator<Board> iterator = vector.iterator();
while(iterator.hasNext()) { //가져올데이터가 있느냐?
Board board = iterator.next(); //있으면 가져와라
System.out.println(board.subject + board.content + board.writer);
}
}
}
용량 : 5
초기 사이즈 : 0
------------------------
객체 추가 후 용량 : 5
객체 추가 후 사이즈 : 5
------------------------
객체 삭제 후 용량 : 5
객체 삭제 후 사이즈 : 3
------------------------
용량 확보 후 용량 : 20
용량 확보 후 사이즈 : 3
------------------------
size값 변경 후 용량 : 20
size값 변경 후 사이즈 : 7
------------------------
null값 삭제 후 용량 : 7
null값 삭제 후 사이즈 : 7
------------------------
size값 변경 후 용량 : 7
size값 변경 후 사이즈 : 3
------------------------
제목1내용1글쓴이1
제목2내용2글쓴이2
제목4내용4글쓴이4
------------------------
제목1내용1글쓴이1
제목2내용2글쓴이2
제목4내용4글쓴이4
List 컬렉션
스텍과 큐(Steck & Queue)
스택 : LIFO 구조 마지막에 저장된 것을 제일 먼저 꺼내게 된다.
큐 : FIFO 구조, 제일 먼저 저장한 것을 제일 먼저 꺼내게 한다.
package kr.co.kihd.stackqueue;
import java.util.LinkedList;
import java.util.Queue;
import java.util.Stack;
public class StackQueueTest {
public static void main(String[] args) {
Stack<String> stack = new Stack<>();
//Queue인터페이스를 구현한 LinkedList클래스 생성 후 대입하고 있음.
Queue<String> queue = new LinkedList<>();
//후입선출(LIFO) -- 마트 매대 우유
stack.push("0");
stack.push("1");
stack.push("2");
//선입선출(FIFO) -- 파이프, 수도관
queue.offer("0");
queue.offer("1");
queue.offer("2");
System.out.println("=스텍=");
while(!stack.isEmpty()) { //비여있는지
System.out.println(stack.pop()); //꺼내는
}
System.out.println("=큐=");
while(!queue.isEmpty()) { //비여있는지
System.out.println(queue.poll()); //꺼내는
}
}
}
=스텍=
2
1
0
=큐=
0
1
2
스텍 예제
package kr.co.kihd.stackqueue;
public class Coin {
private int value;
public Coin(int value) {
this.value = value;
}
public int getValue() {
return this.value;
}
}
package kr.co.kihd.stackqueue;
import java.util.Stack;
public class StackTest {
public static void main(String[] args) {
Stack<Coin> coinBox = new Stack<>();
coinBox.push(new Coin(100));
coinBox.push(new Coin(10));
coinBox.push(new Coin(500));
coinBox.push(new Coin(100));
coinBox.push(new Coin(300));
while(!coinBox.isEmpty()) {
Coin coin = coinBox.pop();
System.out.println("꺼내온 동전 : " + coin.getValue());
}
}
}
큐 예제
package kr.co.kihd.stackqueue;
public class Message {
private String command;
private String to;
//생성자 오버로딩
public Message(String command, String to) {
this.command = command;
this.to = to;
}
//getter
public String getCommand() {
return command;
}
public String getTo() {
return to;
}
}
package kr.co.kihd.stackqueue;
import java.util.LinkedList;
import java.util.Queue;
public class QueueTest {
public static void main(String[] args) {
Queue<Message> mQueue = new LinkedList<Message>();
mQueue.offer(new Message("sendMail", "최지만"));
mQueue.offer(new Message("sendSMS", "류현진"));
mQueue.offer(new Message("sendKakaotalk", "손홍민"));
mQueue.offer(new Message("sendLine", "김덕배"));
while(!mQueue.isEmpty()) {
Message message = mQueue.poll();
switch(message.getCommand()) {
case "sendMail":
System.out.println(message.getTo() + " 에게 메일을 보냅니다.");
break;
case "sendSMS":
System.out.println(message.getTo() + " 에게 SMS를 보냅니다.");
break;
case "sendKakaotalk":
System.out.println(message.getTo() + " 에게 카톡를 보냅니다.");
break;
case "sendLine":
System.out.println(message.getTo() + " 에게 라인를 보냅니다.");
break;
}
}
}
}
Set 컬랙션
특징
수학적 집합에 비유할 수 있다.
저장순서가 유지되지 않는다.
객체를 중복 저장 불가능하다.
하나의 null만 저장 가능하다.
HashSet
특징
통합 객체 및 동등 객체는 중복 저장되지 않는다.
1.번째호출 hashCode()
2.번째호출 equals()
package kr.co.kihd.hashset;
import java.util.HashSet;
import java.util.Iterator;
import java.util.Set;
public class HashSetTest {
public static void main(String[] args) {
Set<String> set = new HashSet<>();
System.out.println("사이즈 : " + set.size());
set.add("java");
set.add("java");
set.add("java");
set.add("java");
set.add("java");
set.add("java");
set.add("java");
set.add("java");
System.out.println("사이즈 : " + set.size());
System.out.println("----------------------");
set.add("JDBC");
set.add("JSP");
set.add("MyBatis");
set.add("MySql");
set.add(null);
set.add(null);
System.out.println("사이즈 : " + set.size());
System.out.println("----------------------");
//반복자 set을 통해서 얻는다.
Iterator<String> iterator = set.iterator();
while(iterator.hasNext()) {
String element = iterator.next(); //객체를 가져오시오
System.out.println(element);
//반복자를 통해서 가져오면 Set에서 객체들을 제거하지 않는다.
System.out.println("사이즈 : " + set.size());
}
System.out.println("----------------------");
set.remove("JDBC");
set.remove("MyBatis");
System.out.println("사이즈 : " + set.size());
System.out.println("----------------------");
for(String str : set) {
System.out.println(str);
}
System.out.println("----------------------");
set.clear();
if(set.isEmpty())
System.out.println("객체가 없습니다.");
else
System.out.println("객체가 존재합니다.");
}
}
사이즈 : 0
사이즈 : 1
----------------------
사이즈 : 6
----------------------
null
사이즈 : 6
java
사이즈 : 6
JSP
사이즈 : 6
MySql
사이즈 : 6
JDBC
사이즈 : 6
MyBatis
사이즈 : 6
----------------------
사이즈 : 4
----------------------
null
java
JSP
MySql
----------------------
객체가 없습니다.
HashSet 오버라이딩 예제
package kr.co.kihd.hashset2;
import java.util.Objects;
public class Member {
private String name;
private int age;
//생성자 오버로딩
public Member(String name, int age) {
super();
this.name = name;
this.age = age;
}
//getter
public String getName() {
return name;
}
public int getAge() {
return age;
}
/* 논리적 동등 객체의 조건
* 1)해쉬코드가 같아야한다. (hashCode() 재정의)
* 2)두개의 객체들의 멤버변수들의 값들이 같아야한다.(equals() 재정의)
*/
/*
* hashCode() : 객체의 hashCode를 리턴함.
* 각 객체의 주소값을 변환하여 생성함.객체의 고유한 정수값.
* 두객체간의 동일객체인지 비교할때 사용할수 있음.
*
*/
//오버라이딩
@Override
public int hashCode() {
System.out.println("해쉬코드 호출");
return Objects.hash(this.name, this.age);
}
// //과거버전 방법 - 하위 호환을 위해 해쉬코드 재정의 방법
// @Override
// public int hashCode() {
// System.out.println("해쉬코드 호출");
// return this.name.hashCode() + this.age;
// }
@Override
public boolean equals(Object obj) {
if(obj instanceof Member) {
Member member = (Member) obj; //Down casting
return (member.name.equals(this.name)&& //동시에 같다면
(member.age == this.age));
}
else {
return false;
}
}
}
Iterator example
package kr.co.kihd.hashset2;
import java.util.HashSet;
import java.util.Iterator;
public class HashSetTEst {
public static void main(String[] args) {
HashSet<Member> set = new HashSet<>();
/*
* new를 사용했기 때문에, 아래에 4개의 Member객체는 서로 다른 주소를
* 가지고 있다. 하지만, Member 클래스에서 hashCode()를 재정의했기에
* 동등객체로 인식한다.
* 즉 Set은 중복저장되지 않는다.
*/
set.add(new Member("최지만", 30));
set.add(new Member("최지만", 30));
set.add(new Member("최지만", 25));
set.add(new Member("최지만", 17));
System.out.println("총 객체수 : " + set.size());
//반복자 사용
Iterator<Member> iterator = set.iterator();
while(iterator.hasNext()) {
Member member = iterator.next(); //객체를 가져오시오
System.out.println(member.getName() + " : " + member.getAge());
}
}
}
해쉬코드 호출
해쉬코드 호출
해쉬코드 호출
해쉬코드 호출
총 객체수 : 3
최지만 : 30
최지만 : 25
최지만 : 17
Map 컬렉션
키와 값으로 구성된 Map.Entry객체를 쌍으로 저장한다.
package kr.co.kihd.hashmap;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.Set;
public class HashMapTest {
public static void main(String[] args) {
//키가 String이고, 값이 Integer이다. 둘다 객체라는 것에 주목하자.
Map<String, Integer> map = new HashMap<>();
System.out.println("사이즈 : " + map.size());
map.put("최지만", 95);
map.put("류현진", 90);
map.put("추신수", 88);
map.put("류현진", 95);
map.put("추신수", 95);
System.out.println("사이즈 : " + map.size());
//map은 중복된 키는 저장하지 않는다. 류현진, 추신수가 2번씩 저장되었다.
//중복저장이 될 경우 마지막에 저장된 값으로 대처가된다.,ㄴ
//중복될 경우 나중에 저장된 값 출력
System.out.println("값 : " + map.get("류현진"));
System.out.println("값 : " + map.get("추신수"));
System.out.println("-----------------------------");
//map컬랙션에 있는 key값만 Set계열로 바꾼다.
Set<String> set = map.keySet();
System.out.println("keySet()을 이용해서 출력해 봄");
//반복자 얻기
Iterator<String> iterator = set.iterator();
while(iterator.hasNext()) {
String key = iterator.next();
//반복자를 통해서 얻은 키값을 가지고 값을 얻어온다
int value = map.get(key);
System.out.println(key + " : " + value);
}
System.out.println("------------------------------");
//Map컬렉션의 Map.Entry객체를 대상으로 Set계열로 바꾼다.
Set<Map.Entry<String, Integer>> entrySet = map.entrySet();
System.out.println("entrySet()을 이용해서 출력해 봄");
//반복자 얻기
Iterator<Map.Entry<String, Integer>> entryIterator = entrySet.iterator();
while(entryIterator.hasNext()) {
Map.Entry<String, Integer> entry = entryIterator.next();
String key = entry.getKey(); //키값을 얻는다.
int value = entry.getValue(); //값을 얻는다.
System.out.println(key +" : " +value);
}
System.out.println("------------------------------");
//전체 객체 삭제
map.clear();
System.out.println("총 MapEntry 수 : " + map.size());
}
}
student example
package kr.co.kihd.hashmap2;
import java.util.Objects;
public class Student {
private int sno; //학번
private String name; //이름
//생성자 오버로딩
public Student(int sno, String name) {
this.sno = sno;
this.name = name;
}
//getter
public int getSno() {
return sno;
}
public String getName() {
return name;
}
@Override
public int hashCode() {
return Objects.hash(this.sno, this.name); //자동으로 해쉬코드값을 생성해준다.
}
//하위 호환성 고려
// @Override
// public int hashCode() {
// return this.sno + this.name.hashCode(); //자동으로 해쉬코드값을 생성해준다.
// }
@Override
public boolean equals(Object obj) {
if(obj instanceof Student) {
Student student = (Student) obj;
return this.sno == student.sno && this.name.equals(student.name);
}
return false;
}
}
package kr.co.kihd.hashmap2;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.Set;
public class HashMapTest {
public static void main(String[] args) {
Map<Student, Integer> map = new HashMap<>();
//키 객체가 동등객체라면 중복 저장하지 않는다.
map.put(new Student(1001, "최지만"), 95);
map.put(new Student(1001, "최지만"), 90);
map.put(new Student(1001, "류현진"), 100);
map.put(new Student(1001, "추신수"), 80);
//ket 객체의 중복은 허용되지 않음
System.out.println("총 Entry 수 : " + map.size());
//위에 저장된 것으로 대체됨.
System.out.println("최지만 : " + map.get(new Student(1001, "최지만")));
Set<Student> set = map.keySet();
System.out.println("keySet()을 이용해서 출력해 봄");
//반복자 얻기
Iterator<Student> keyiterator = set.iterator();
while(keyiterator.hasNext()) {
Student key = keyiterator.next();
System.out.println("학번 : " + key.getSno() + ", "
+"이름 : " + key.getName() + ", "
+"점수 : " + map.get(new Student(key.getSno(), key.getName())));
}
}
}
Hashtable
HashMap : 신버전
Hashtable : 구버전