WEB JAVA SPRING/문법

List, Map, Set

sshhhh 2023. 8. 24. 16:31

== 데이터의 집합==

Java Collection에는 List, Map, Set 인터페이스를 기준으로 여러 구현체가 존재한다.

이에 더해 Stack과 Queue 인터페이스도 존재한다.

Q.왜 이러한 Collection 을 사용하는 것일까?
A1.다수의 Data 를 다루는데 표준화된 클래스들을 제공해주기 때문에 DataStructure를 직접 구현하지 않고
     편하게 사용할 수 있기 때문이다.
A2.배열과 다르게 객체를 보관하기 위한 공간을 미리 정하지 않아도 되므로, 객체의 수를 동적으로 정할 수 있다.         이는 프로그램의 공간적인 효율성 또한 높여준다.

 


List 

- 순서O, 데이터 중복O

- 가변적인 크기(ArrayList는 list를 배열 형태로 구현한 것으로 크기가 자동으로 조정된다.)

- 데이터를 순서에 맞게 저장, Index를 부여한다. -> 특정 index에 데이터를 삽입하거나 접근할 수 있다.

ArrayList
- 크기를 마음대로 조절할 수 있는 배열
- 단방향 포인터 구조로 자료에 대한 순차적인 접근에 강점이 있음

LinkedList
- 양방향 포인터 구조로 데이터의 삽입, 삭제가 빈번할 경우 빠른 성능을 보장.
- 메모리 많이 차지
- 스택, 큐, 양방향 큐 등을 만들기 위한 용도로 쓰임

 

문자열 ArrayList를 생성 ArrayList list = new ArrayList();
생성된 ArrayList 객체에
데이터 순서대로 저장
add(data)
특정위치에 추가 set(index,data)
~제거 remove(index)
가져오기 get(index) 
크기 size()
저장된 위치  IndexOf(데이터)
  • 그런데 ArrayList는 동일한 데이터가 여러 번 저장될 수 있기 때문에 맨 처음에 있는 데이터의 위치가 검색되어 반환된다. 검색을 반대 방향으로 하려면, lastIndexOf(데이터) 메소드를 사용한다.

 

실습1

import java.util.*;
import java.util.Vector;

public class MB_Exam17_Generi {

	public static void main(String[] args) {
		
		Scanner input = new Scanner(System.in); 
		
		
		ArrayList <String> list = new ArrayList<String>();
		int i , j;
		///////////////////////////////
		list.add("Milk"); //0번째 위치에다 Milk를 저장한다.
		list.add("Bread"); //1번째 위치에다 Bread를 저장한다.
		list.add("Butter"); //2번째 위치에다 Butter를 저장한다.
		
		System.out.println("Size="+list.size());
		for(i=0;i<=list.size()-1;i++) {
			System.out.println("list["+i+"]="+list.get(i));
		}
	
		//////////////////////////
		list.add(1,"apple"); //1위치에다 Apple을 추가한다. 크기가 1 증가하게 된다.
		
		System.out.println();
		System.out.println();
		
		System.out.println("Size="+list.size());
		for(i=0;i<=list.size()-1;i++) {
			System.out.println("list["+i+"]="+list.get(i));
		}
		
		////////////////////////////////////////
		list.set(2, "Sweet");//2위치에 있는것을 Sweet으로 수정한다. 크기는 그대로다.
		System.out.println();
		System.out.println();
		
		
		System.out.println("Size="+list.size());
		for(i=0;i<=list.size()-1;i++) {
			System.out.println("list["+i+"]="+list.get(i));
		}
		


		///////////////////////////////////////////////
		
		list.remove(1); //위치 1에 있는 원소를 제거한다. 그래서 크기는 1 줄어든다.
		
		System.out.println();
		System.out.println();
		
		
		System.out.println("Size="+list.size());
		for(i=0;i<=list.size()-1;i++) {
			System.out.println("list["+i+"]="+list.get(i));
		}
		/////////////////////////////////////////////////
		j=list.indexOf("Sweet);"
		
	System.out.println();
	System.out.println();
							
	System.out.println("Size="+list.size());
	for(i=0;i<=list.size()-1;i++) {
	System.out.println("list["+i+"]="+list.get(i));
				}
	System.out.println("Index of Sweet = "+j)	} }

 

출력

실습2

List 소스코드

package kr.co.mlec.day02;

import java.util.ArrayList;
import java.util.List;
import java.util.Random;

/*
 * List: 순서(o), 중복 (o)
 * 	- ArrayList
 * 	- LinkedList
 * 
 * Wrapper class (기본자료형-> 참조자료형)
 *	기본자료형		참조자료형(
 *	boolean		Boolean
 *	char		Character
 *	byte		Byte
 *	short		Short
 *	int			Integer
 *	long		Long
 * 	float		Float
 * 	double 		Double
 * 
 * 
 * class Integer  {
 *  private int data;
 * }
 */
public class ListMain {		//클래스 이름 작성

	public static void main(String[] args) {		// 메인함수 작성
		
		//List<String> list = new ArrayList<String>();
		List<String> list = new ArrayList<>(); 	//변수 list의 쓰임이 뭘까 정의, ArrayList를 만들기 위한 변수
		// JDK 1.7버전부터 뒤에는 작성 안해도 인식 가능, 제네릭
		//묵시적 형변환 가능  
		//<>제너릭 오직 레퍼런스 타입만 가능하여 기본자료형인 int 사용 불가능 
		
		list.add("one");
		list.add("two");
		list.add("three");
		list.add("four");
		list.add("one");	//하나씩 데이터를 삽입해(add) 씀
		//Arraylist는 중복가능
		
		System.out.println("원소의 총 개수: "+ list.size());	//몇개있는지 size 씀
		
		System.out.println("0번지 위치한 데이터: " + list.get(0));	// 0번째 가져왔다 get으로
		
		String removestr = list.remove(0);	// 0번째 지웠다. + 특징: 삭제 후에는 뒤에 있던 애들 앞으로 떙겨짐
		
		System.out.println("0번지 삭제 데이터:" + removestr);	// removerstr : 삭제 데이터를 저장해 놓겠다 
		
		System.out.println("0번지 삭제 후 0번지 위치한 데이터: " + list.get(0));		// 삭제된 데이터가 뭔지 보여주자
		
		boolean bool = list.contains("three");		// bool: list에 저 three가 있냐
		if(bool) {	// if문: bool에 three있으면 
			System.out.println("three는 존재합니다");
		}else {
			System.out.println("three는 존재하지 않습니다.");
		}
		
		if(list.remove("three")) {
			System.out.println("삭제 성공");
		}else {
			System.out.println("삭제 실패");	
		}
		bool = list.contains("three");		//변수를 다시 가져다 쓴,,,
		if(bool) {
			System.out.println("three는 존재합니다");
			
		}else {
			System.out.println("three는 존재하지 않습니다.");
		}
		//전체데이터 출력하자
		System.out.println("< 전체 데이터 출력 - 첫번쨰 방식 >");
		for (int i = 0; i < list.size(); i++) {		// size 만큼 돌리겠다 
			System.out.println(list.get(i));		// get으로 데이터 추출
		}
		System.out.println("< 전체 데이터 출력 - 두번쨰 방식 >");	// 출력할 때만 사용 가능 
		for (String str:list) {								// 향상된 for문
			System.out.println(str);
		}
	}

}

 

List - 콘솔 출력

원소의 총 개수: 5
0번지 위치한 데이터: one
0번지 삭제 데이터:one
0번지 삭제 후 0번지 위치한 데이터: two
three는 존재합니다
삭제 성공
three는 존재하지 않습니다.
< 전체 데이터 출력 - 첫번쨰 방식 >
two
four
one
< 전체 데이터 출력 - 두번쨰 방식 >
two
four
one

Map

- 키(key)와 값(value)의 쌍
- 순서X, key 중복X , value 중복O

- 검색 속도 빠름
- index 존재 X, iterator 사용

HashMap
- Map 인터페이스를 구현하기 위해 해시테이블을 사용한 클래스
- Key에 대한 중복이 없으며 순서를 보장하지 않는다.
- Key와 Value 값으로 NULL을 허용한다.
- 동기화가 보장되지 않는다.
- 검색에 가장 뛰어난 성능을 가진다.
HashTable
- 동기화가 보장되어 병렬 프로그래밍이 가능하고 HashMap 보다 처리속도가 느리다.
- Key와 Value 값으로 NULL을 허용하지 않는다.
LinkedHashMap
- 입력된 순서를 보장한다.
TreeMap
- 이진 탐색 트리(Red-Black Tree)를 기반으로 키와 값을 저장한다.
- Key 값을 기준으로 오름차순 정렬되고 빠른 검색이 가능하다.
- 저장 시 정렬을 하기 때문에 시간이 다소 오래 걸린다.

HashMap

put - key, value 추가 

import java.util.HashMap;

public class Sample {
    public static void main(String[] args) {
        HashMap<String, String> map = new HashMap<>();
        map.put("people", "사람");
        map.put("baseball", "야구");
    }
}

get 으로 접근

import java.util.HashMap;

public class Sample {
    public static void main(String[] args) {
        HashMap<String, String> map = new HashMap<>();
        map.put("people", "사람");
        map.put("baseball", "야구");
        System.out.println(map.get("people")); // "사람" 출력
    }
}

containsKey - 맵에 해당 key가 있는지를 참(true) 또는 거짓(false)으로 리턴한다.

(... 생략 ...)
HashMap<String, String> map = new HashMap<>();
map.put("people", "사람");
map.put("baseball", "야구");
System.out.println(map.containsKey("people"));  // true 출력

 

remove - 맵의 항목을 삭제, 해당 key의 항목을 삭제한 후 value 값을 리턴한다.

(... 생략 ...)
HashMap<String, String> map = new HashMap<>();
map.put("people", "사람");
map.put("baseball", "야구");
System.out.println(map.remove("people"));  // "사람" 출력

나머지 메소드 참고 :  https://wikidocs.net/208 

 

 

실습

Map 소스코드

package kr.co.mlec.day02;

import java.util.HashMap;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Set;

/*
 * Map: key, value 쌍으로 구성된 데이터의 집합
 * 		순서(x), key에 대한 중복(x)
 *	- HashMap
 *	- TreeMap 
 */
	public class MapMain {	
    
	public static void main(String[] args) {	
		// TODO Auto-generated method stub		
 	Map<String,String> map = new HashMap<>();	//String 타입인 key,value map 변수로 저장 , HaspMap 클래스 생성
 				//키		//밸류
		map.put("1", "ONE");
		map.put("2", "TWO");
		map.put("3", "THREE");
		map.put("4", "FOUR");		// map에 4개 넣음

		System.out.println("원소의 개수: " + map.size()); 		// map 안에 몇개 있음?
		
		System.out.println("key : 1 ===> value : "+ map.get("1"));		// key가 1일 때 value는?  get(): value값 가져오기
		System.out.println("key : 5 ===> value : "+ map.get("5"));		//	key가 5일 때 value는?  없음
		
		map.put("1","하나");	// key 1 value 하나 추가용: put은 동일한 값이 있을 경우 새로운 값으로 대체하고 기존 값 반환
		System.out.println("key : 1 ===> value : " + map.get("1")); 
		
//		key = 5인 데이터가 없으면 key:5, value: "FIVE" 삽입
		if(!map.containsKey("5")) {		
			map.put("5","FIVE");
		}
		System.out.println("key : 5 ===> value : "+ map.get("5"));
		
		System.out.println("<전체 데이터 출력 - 첫번째 방식>");
		
		Set<Entry<String, String>> entry = map.entrySet();		
		//Set<Map.Entry<K, V>> entrySet() :(key 와 value) 쌍을 표현하는 Map.Entry 집합을 반환
		//실제 entry에 있으니 entrySet으로 잡아 날라와라
		// set 형이 가지고 있는 데이터 타입이 Entry
		for(Entry<String,String> e :entry) {
			System.out.println("key : " +e.getKey() + ", value: " + e.getValue()	
			);
		}
		
		System.out.println("<전체 데이터 출력 - 두번째 방식>");		//key 만 뽑아서 데이터 출력
		Set<String> keys = map.keySet();
		for(String key : keys) {
			System.out.println("key: " + key + ", value : " + map.get(key));
		}
	
		
	}

}

 

Map 콘솔

원소의 개수: 4
key : 1 ===> value : ONE
key : 5 ===> value : null
key : 1 ===> value : 하나
key : 5 ===> value : FIVE
<전체 데이터 출력 - 첫번째 방식>
key : 1, value: 하나
key : 2, value: TWO
key : 3, value: THREE
key : 4, value: FOUR
key : 5, value: FIVE
<전체 데이터 출력 - 두번째 방식>
key: 1, value : 하나
key: 2, value : TWO
key: 3, value : THREE
key: 4, value : FOUR
key: 5, value : FIVE

 

Map 소스코드(비밀번호 변경)

package kr.co.mlec.day02;	

import java.util.HashMap;
import java.util.Map;
import java.util.Scanner;
import java.util.Set;

public class MapMain02 {

	public static void main(String[] args) {
		// TODO Auto-generated method stub

		Map<String, String> members = new HashMap<>();

		members.put("aaa","1111");
		members.put("bbb","2222");
		members.put("ccc","3333");
		members.put("ddd","4444");
		
		System.out.println("< 비밀번호 변경서비스 입니다 >");
		System.out.println("회원님의 아이디를 입력하세요 : ");

		Scanner sc = new Scanner(System.in);
		String id = sc.nextLine();
		
		if(!members.containsKey(id)) {
			System.out.println("입력하신 아이디 [" + id + "]는 존재하지 않습니다.");
			System.out.println("변경서비스를 종료합니다.");
			System.exit(0);
		}
		System.out.println("현재 패스워드를 입력하세요 : ");
		String password = sc.nextLine();
		if(!members.get(id).equals(password)) {//문자열 비교시 equals 사용
			System.out.println("패스워드가 일치하지 않습니다");
			System.out.println("변경서비스를 종료합니다.");
			System.exit(0);
		}
		
		System.out.println("변경할 패스워드를 입력하세요 : ");
		String newPassword = sc.nextLine();
		members.put(id,newPassword);
		System.out.println("패스워드 변경이 완료되었습니다.");
		
		System.out.println("< 회원 정보 출력 >");
		System.out.println("----------------------------------");
		System.out.println("\tID\tPASSWORD");
		System.out.println("----------------------------------");
		Set<String> keys = members.keySet();
		for(String key : keys) {
			System.out.println("\t" + key + "\t" + members.get(key));
		}
		System.out.println("----------------------------------");
	}

}

 

Map 콘솔

< 비밀번호 변경서비스 입니다 >
회원님의 아이디를 입력하세요 : 
ccc
현재 패스워드를 입력하세요 : 
3333
변경할 패스워드를 입력하세요 : 
1111
패스워드 변경이 완료되었습니다.
< 회원 정보 출력 >
----------------------------------
	ID	PASSWORD
----------------------------------
	aaa	1111
	ccc	1111
	bbb	2222
	ddd	4444
----------------------------------
 

Set

- 순서X, 데이터 중복X

- 검색 속도 빠름
- index 존재 X, iterator 사용

HashSet
- 인스턴스의 해시값을 기준으로 저장하기 때문에 순서를 보장하지 않는다.
- NULL 값을 허용한다.
- 가장 빠른 임의 접근 속도
LinkedHashSet
- 입력된 순서를 보장한다.
TreeSet
- 이진 탐색 트리(Red-Black Tree)를 기반으로 한다.
- 정렬된 순서대로 보관하며 정렬 방법을 지정할 수 있음
- 데이터 삽입, 삭제에는 시간이 걸리지만 검색, 정렬이 빠르다.

 

 

Set 소스코드

package kr.co.mlec.day02;

import java.util.Iterator;
import java.util.Set;
import java.util.TreeSet;

/*
 *  set : 순서(x), 중복(x)
 *  	- HashSet
 *  	- TreeSet 인터페이스
 *  	- get 함수 x
 */
public class SetMain {

	public static void main(String[] args) {
		// TODO Auto-generated method stub		
		//Set<String> set = new HashSet<>();
		Set<String> set = new TreeSet<>();
		set.add("one"); 	// Set에 "one" 데이터 추가
		set.add("two");
		set.add("three");
		set.add("four");
		set.add("five");
		boolean bool= set.add("one");	// bool에 원이라는 데이터가 있는지 없는지 출력 확인하기 위해서~
		
		System.out.println(bool ? "삽입성공" : "삽입실패");	//? 삼항연산자로  true 면 삽입~ false면 실패~
		
		System.out.println("원소의 총 개수: " + set.size()); 	// size로  set 안에 원소 몇개 있는지 알랴줌
		
		// 1.5 버전의 for문이용
		System.out.println("< 전체 데이터 출력 - 첫번째 방식>");
		for (String str :set) {		//향상된 for문 - 문자열을 반복문 ㄱ
			System.out.println(str);	//hash 코드 값 기준으로 순서가 무작위로 나온다
		// String으로 오름차순으로 출력됨.
			
		// 2. toArray() 메소드 이용
			System.out.println("<전체 데이터 출력 - 두번째 방식>");
			Object[] arr = set.toArray();	//순서가 없는 상태인 애들을 배열로 넣어 사용 한다 --> index 와 향상된 for문 사용 가능
			for (int i = 0 ; i< arr.length ; i++) {
				System.out.println(arr[i]);
			}
			//for(int i = 0; i <arr.length ; i++){
			//String str = (String)arr[i];
			//System.out.println("[" + arr[i] + "]", length : " + str.length());}
		}
	/*
	 * Iterator(순환자) 주요메소드
	 * - hasNext():다음 데이터의 존재여부 판단
	 * - next() : 데이터 접근 (다음 데이터로 이동)
	 * 
	 */
		System.out.println("<전체 데이터 출력 - 세번째 방식>");
		Iterator<String> ite = set.iterator();		// 반복자
		while(ite.hasNext()) {		//무한반복인 while은 true를 받으니까 hasNext를 사용(hasNext: 불린타입으로 출력)
			String str = ite.next();
			System.out.println(str);
		}
	}
	
}

 

Set 콘솔 출력

삽입실패
원소의 총 개수: 5
< 전체 데이터 출력 - 첫번째 방식>
five
<전체 데이터 출력 - 두번째 방식>
five
four
one
three
two
four
<전체 데이터 출력 - 두번째 방식>
five
four
one
three
two
one
<전체 데이터 출력 - 두번째 방식>
five
four
one
three
two
three
<전체 데이터 출력 - 두번째 방식>
five
four
one
three
two
two
<전체 데이터 출력 - 두번째 방식>
five
four
one
three
two
<전체 데이터 출력 - 세번째 방식>
five
four
one
three
two

 

 

 

 

 

 

 

참고: https://cocoon1787.tistory.com/527, https://hackersstudy.tistory.com/26