국비 17

냐아암·2023년 5월 10일
0

국비

목록 보기
23/114

컬렉션

  • Collection 인터페이스: List, Set의 공통 코드를 작성한 단순한 부모 인터페이스
  • Java Collection: 자바의 자료 구조 모음(List, Set, Map)


  • ArrayList(용량): 기본생성자(기본적으로 크기는 10)
    용량만큼의 리스트를 생성 -> 용량 너무 크면 메모리 소모 큼
    (검색/조회에 효율적)
  • 제네릭스(Generics): 컬렉션에 저장되는 객체 타입을 한 가지로 제한
    List<타입> 리스트명 = new ArrayList<타입>();

    List<Student> studentList = new ArrayList<Student>();
  • LinkedList(): 체인처럼 관리 (추가 수정에 효율적)
    List<Student> studentList = new LinkedList<Student>();

  • List.add(Object e): 리스트에 객체 추가
    (여러 타입의 데이터 저장할 수 있음) (add() 무조건 true 값)
    배열에서
    arr[i] = new Person(......)과 비슷한 역할

    studentList.add(new Student ("유저일", 22, "인천시 계양구", 'M', 50));
    studentList.add(sc);

  • List.get(index i): i번째 인덱스에 있는 값 반환
    배열에서
    print(arr[i])와 비슷한 역할

    studentList.get(0)

  • int List.size(): List에 저장된 데이터 개수 얻어오기
    배열에서
    배열명.length와 비슷한 역할

    if(studentList.size() == 0)

  • List.isEmpty(): List가 비어있으면 true
    List.get(index i) == null 쓰지 않음
    if(studentList.isEmpty())

  • List.set(int index, 자료형 e): List의 i번째 요소를 전달받은 e로 변경
    -> 반환값에는 변경 전 객체가 담겨있음
    Student temp = studentList.set(index, new Student(name, age, region, gender, score)); //기존 정보 temp에 담기

  • List.remove(int index): List에서 index번째 요소 제거 (이때 제거된 요소 반환)
    -> List는 중간에 비어있는 인덱스를 없게 하기 위해 remove() 동작 시 뒤쪽 요소를 한 칸씩 당겨온다.
    Student temp = studentList.remove(index); //기존 정보 temp에 담기

  • String.contains(문자열): String에 문자열이 포함되어 있으면 true, 아니면 false (사용 시 순서 주의)
    std.getName().contains(input)


향상된 for문

컬렉션, 배열의 모든 요소를 순차적(0번 인덱스부터 마지막 요소까지 인덱스를 1씩 증가)으로 반복, 접근할 수 있는 for문

[작성법]
for(컬렉션 or 배열에서 꺼낸 한 개의 요소를 저장할 변수 : 컬렉션명 or 배열명) {}

Student

package edu.kh.collection.model.vo;

public class Student {
	
	//필드
	private String name;
	private int age;
	private String region;
	private char gender;
	private int score;
	
	
	//생성자
	public Student() {}

	public Student(String name, int age, String region, char gender, int score) {
		this.name = name;
		this.age = age;
		this.region = region;
		this.gender = gender;
		this.score = score;
	}

	
    //메소드
	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	public int getAge() {
		return age;
	}

	public void setAge(int age) {
		this.age = age;
	}

	public String getRegion() {
		return region;
	}

	public void setRegion(String region) {
		this.region = region;
	}

	public char getGender() {
		return gender;
	}

	public void setGender(char gender) {
		this.gender = gender;
	}

	public int getScore() {
		return score;
	}

	public void setScore(int score) {
		this.score = score;
	}

	
	//toString() 오버라이딩 자동완성
	//alt shift S S(Generate toString()) enter
	@Override
	public String toString() {
		return "Student [name=" + name + ", age=" + age + ", region=" + region + ", gender=" + gender + ", score="
				+ score + "]";
	}
	
	
	
	
	
	
	
	
	
	

}

StudentService

package edu.kh.collection.model.service;

import java.util.ArrayList;
import java.util.InputMismatchException;
import java.util.LinkedList;
import java.util.List;
import java.util.Scanner;

import edu.kh.collection.model.vo.Student;

public class StudentService {
	
	//필드
	private Scanner sc = new Scanner(System.in);
	
	//학생 정보를 저장할 List(객체 배열의 Upgrade 버전)
	
	//import java.util.List; 인터페이스: List에 반드시 필요한 필수 기능을 모아둔 인터페이스
	// *인터페이스는 객체 생성 불가 , but 부모 참조변수로 사용 가능
	
//	List studentList = new List();
	//인터페이스는 모든 메소드가 추상 메소드(미완성 메소드)
	//미완성된 부분이 존재하는 클래스이기 때문에 객체 생성 불가
	
	
	//ArrayList() 기본생성자: 기본 크기가 10칸짜리 리스트 생성
	//					--> 하지만 리스트는 크기가 변동하기 때문에 큰 의미 없음
	
	//ArrayList(용량): 용량만큼의 리스트를 생성
	//				--> 너무 큰 값을 작성하면 메모리를 많이 소모함
	
//	private List<Student> studentList = new ArrayList<Student>(); //검색(조회)에 효율적
	private List<Student> studentList = new LinkedList<Student>(); //추가 수정 삭제에 효율적
	//Student로 저장되는 타입이 제한된 리스트 생성
	// == Student만 저장 가능 == 모든 게 Student 
	// == Student 임을 검사할 필요 없음
	
	
	public StudentService() {
		
		studentList.add(new Student ("박서준", 25, "서울시 중구", 'M', 90));
		studentList.add(new Student ("정해인", 23, "서울시 강남구", 'M', 80));
		studentList.add(new Student ("박보영", 20, "서울시 종로구", 'F', 90));
		studentList.add(new Student ("김민서", 33, "대전 서구", 'F', 100));
		studentList.add(new Student ("유저일", 22, "인천시 계양구", 'M', 50));
	}
	
	
	
	public void ex() {
		//List 테스트
		
		//List.add(Object e): 리스트에 객체를 추가
		// *매개변수 타입이 Object == 모든 객체를 매개변수로 전달할 수 있다.
		//	(매개변수 Object == 최상위 부모 참조 변수 == 다형성 적용 가능)
		
		studentList.add(new Student()); //0번 인덱스
//		studentList.add(sc);			//1번 인덱스
//		studentList.add("문자열");		//2번 인덱스
//		studentList.add( new Object());	//3번 인덱스
		// -> 컬렉션 특징: 여러 타입의 데이터 저장할 수 있다.
		
		//(반환형) 
		//Object List.get(index i): 리스트에서 i번째 인덱스에 있는 객체(Object)를 반환
		//반환형이 Object == 모든 객체를 반환할 수 있다.
		
		System.out.println(studentList.get(0)/*.toString()*/);
		//결과: Student [name=null, age=0, region=null, gender=
		// 실행 전: java.lang.Object.toString() == 정적 바인딩
		// 실행 후: 0번째에는 Student 객체이고, toString()이 오버라이딩 되어있다.
		//			-> Student의 toString()이 수행됨 == 동적 바인딩
		
		//Student의 이름만 얻어오기
		//Student 객체가 맞는지 확인하고 다운 캐스팅을 해야
		//Student 기능을 사용할 수 있다.
		if(studentList.get(0) instanceof Student) {
			System.out.println("Student 타입 맞아요");
		}
		// -> 길고 복잡
		// --> 컬렉션의 장점인 여러 객체 저장이 코딩에 방해됨
		
		//=========> 제네릭스 (Generics)
		//(보통은 제네릭이라고 함) <>
		//[제일 중요한 역할]
		// -> 컬렉션에 저장되는 객체 타입을 한 가지로 제한해줌
		
		System.out.println(studentList.get(0).getName()); //제네릭 후
		
		
		System.out.println(((Student)studentList.get(0)).getName()); //제네릭 전
		//getName은 Student 메소드라서 Student로 강제 형변환 (다운 캐스팅)
		//(.은 우선 연산자라 () 괄호로 묶음)
		
		
	}
	
	//메소드 설명용 주석
	/** 
	 * 메뉴 출력용 메소드
	 * @author user1
	 * */
	public void displayMenu() { //alt shift J 누르면 설명용 주석 자동 완성
		
		int menuNum = 0;
		
		do {
			
			System.out.println("\n====학생 관리 프로그램====");
			System.out.println("1. 학생 정보 추가");
			System.out.println("2. 학생 전체 조회");
			System.out.println("3. 학생 정보 수정");
			System.out.println("4. 학생 정보 제거");
			System.out.println("5. 이름으로 검색(일치)");
			System.out.println("6. 이름으로 검색(포함)");
			
			System.out.println("0. 프로그램 종료");
			
			System.out.print("\n메뉴 번호 선택 >> ");
			
			
			try {
				menuNum = sc.nextInt();
				System.out.println();
				
				switch(menuNum) {
				case 1 : System.out.println(addStudent()); break;
				case 2 : selectAll(); break;
				case 3 : System.out.println(upDateStudent()); break;
				case 4 : System.out.println(removeStudent()); break;
				case 5 : searchName1(); break;
				case 6 : searchName2(); break;
				
				case 0 : System.out.println("<프로그램 종료>"); break;
				
				default : System.out.println("메뉴에 작성된 번호만 입력해주세요.");
				
				}
				
			}catch(InputMismatchException e) {
				System.out.println("\nerror: 입력 형식이 유효하지 않습니다. 다시 시도해주세요.");
				sc.nextLine(); //입력버퍼에 잘못 입력된 문자열 비우기 
				
				menuNum = -1;
				//첫 반복 시 잘못 입력하는 경우, menuNum 값이 0이라서 종료되는데
				//이를 방지하기 위해 -1 대입
			}
			
			
		}while(menuNum != 0);
		
	}
	
	/**
	 * 1. 학생 정보 추가 메소드
	 * 	  - 추가 성공 시 "성공", 실패 시 "실패" 문자열 반환
	 */
	public String addStudent() throws InputMismatchException {
		
		System.out.println("=====학생 정보 추가=====");
		
		System.out.print("이름: ");
		String name = sc.next();
		
		System.out.print("나이: ");
		int age = sc.nextInt();
		
		sc.nextLine();
		
		System.out.print("사는 곳: ");
		String region = sc.nextLine();
		
		System.out.print("성별(M/F): ");
		char gender = sc.next().charAt(0);
						// String -> char
		
		System.out.print("점수: ");
		int score = sc.nextInt(); //정수가 아닌 값 입력 InputMismatchException
		// 이미 displayMenu(호출한 곳)에서 동일 예외 처리하고 있으니 throws로 던져줌
		
		//Student 객체 생성 후 List에 추가
		if(studentList.add(new Student(name, age, region, gender, score))) {
			//boolean java.util.List.add(Student e)
			//(반환형)					--> 제네릭 <Student> 때문에 List 타입이 Student로 제한됨
			
			//add() 무조건 true를 반환하기 때문에
			//실패하는 경우는 없음
			//대신, 예외가 발생해서 add() 수행 전 메소드가 종료될 순 있음
			
			return "성공";
		}else {
			return "실패";
		}
		
	}
	
	/**
	 * 2. 학생 전체 조회 메소드
	 */
	public void selectAll() {
		
		//-List는 인덱스가 있다.(0부터)
		//-List에 저장된 데이터의 개수를 얻어오는 방법: int List.size()
		//cf) 배열명.length 대신 사용
		
		//List가 비어있는지 확인하는 방법
		//boolean List.isEmpty(): 비어있으면 true 반환
		
		
		System.out.println("=====학생 전체 조회=====");
		
		//studentList가 비어있는 경우 "학생 정보가 없습니다." 출력
		
//		if(studentList.size() == 0) { //null 쓰지 않음
		if(studentList.isEmpty()) {
			System.out.println("학생 정보가 없습니다.");
			return; //현재 메소드를 종료하고 호출한 곳으로 돌아감
					//단, 반환값은 없음(void)
			//else 대신 작성
		}
		
		/* 일반적인 for문
		for(int i =0; i<studentList.size(); i++) {
			System.out.println(studentList.get(i));
								//studentList에서 i번째 인덱스 요소 출력
			
		}
		*/
		
		//향상된 for문(for each문)
		//-컬렉션, 배열의 모든 요소를 순차적으로 반복 접근할 수 있는 for문
		// (순차적: 0번 인덱스부터 마지막 요소까지 인덱스를 1씩 증가)
		
		//[작성법]
		// for(컬렉션 또는 배열에서 꺼낸 한 개의 요소를 저장할 변수: 컬렉션명 or 배열명) {}
		
		int index = 0;
		for(Student std : studentList) {
			//std에는 for문 반복마다 0, 1, 2, ... 인덱스 요소들 한 번씩 저장
			
			System.out.print((index++)+ "번: ");
			System.out.println(std);
		}
		
	}
	
	/**
	 * 3. 학생 정보 수정 메소드
	 */
	public String upDateStudent() throws InputMismatchException{
		
		// -Student List.set(int index, Student e)
		//			-> List의 i번째 요소를 전달받은 e로 변경
		//			-> 반환값 Student == 변경 전 Student 객체가 담겨있음
		
		System.out.println("=====학생 정보 수정=====");
		
		System.out.print("인덱스 번호 입력: ");
		int index = sc.nextInt();
		sc.nextLine();
		
		//1) 학생 정보가 studentList에 있는가?
		if(studentList.isEmpty()) { //비어있을 경우
			return "입력된 학생 정보가 없습니다.";
			
			//2) 입력된 숫자가 0보다 작은가?(음수 검사)
		} else if(index<0) {
			return "음수는 입력할 수 없습니다.";
			
			//3) 만약 문자열을 입력한 경우 -> throws로 예외 처리
			
			//4) 입력받은 숫자가 studentList 범위 내 인덱스 번호인가?
		} else if(index>=studentList.size()) {
			return "범위를 넘어선 값을 입력할 수 없습니다.";
		} else {
			//수정 코드 작성
			
			System.out.println(index + "번째 인덱스에 저장된 학생 정보");
			
			System.out.println(studentList.get(index));
			//전에 저장되어 있던 정보 출력
			
			System.out.print("이름 : ");
			String name = sc.next();

			System.out.print("나이 : ");
			int age = sc.nextInt();
			sc.nextLine(); // 입력 버퍼 개행 문자 제거

			System.out.print("사는곳 : ");
			String region = sc.nextLine();

			System.out.print("성별(M/F) : ");
			char gender = sc.next().charAt(0);
			// String -> char

			System.out.print("점수 : ");
			int score = sc.nextInt(); // InputMismatchException
			
			
			//입력받은 index번째에 새로운 학생 정보로 수정
			//이때 index번째에 있던 기존 학생 정보가 반환된다.
			Student temp = studentList.set(index, new Student(name, age, region, gender, score));
			
			return temp.getName() + "님의 정보가 변경되었습니다.";
		}
		
		
	}
	
	/**
	 * 4. 학생 정보 제거 메소드
	 */
	public String removeStudent() throws InputMismatchException{
		
		// - Student List.remove(int index)
		//	 리스트에서 index번째 요소를 제거
		//	 이때, 제거된 요소 반환
		
		// *List는 중간에 비어있는 인덱스가 없게 하기 위해
		//	remove() 동작 시 뒤쪽 요소를 한 칸씩 당겨온다.
		
		System.out.println("=====학생 정보 제거=====");
		
		System.out.print("인덱스 번호 입력: ");
		int index = sc.nextInt();
		sc.nextLine();
		
		//1) 학생 정보가 studentList에 있는가?
		if(studentList.isEmpty()) { //비어있을 경우
			return "입력된 학생 정보가 없습니다.";
			
			//2) 입력된 숫자가 0보다 작은가?(음수 검사)
		} else if(index<0) {
			return "음수는 입력할 수 없습니다.";
			
			//3) 만약 문자열을 입력한 경우 -> throws로 예외 처리
			
			//4) 입력받은 숫자가 studentList 범위 내 인덱스 번호인가?
		} else if(index>=studentList.size()) {
			return "범위를 넘어선 값을 입력할 수 없습니다.";
		} else {
			//학생 정보 제거
			
			System.out.print("정말 삭제하시겠습니까? (Y/N): ");
			char ch = sc.next().toUpperCase().charAt(0);
					//String -> 대문자 String -> 0번째 인덱스 문자
					//String.toUpperCase(): 문자열을 대문자로 변경
			
			if(ch == 'Y') {
				Student temp = studentList.remove(index);
				return temp.getName() + "님의 정보가 제거되었습니다.";
				
			} else {
				return "취소";
			}
			
		}
		
	}
	
	/**
	 * 5. 이름이 일치하는 학생을 찾아서 조회하는 메소드
	 */
	public void searchName1() {
		
		System.out.println("=====학생 검색(이름 일치)=====");
		
		System.out.print("검색할 이름 입력: ");
		String input = sc.next();
		
		
		boolean flag = true;
		
		//향상된 for문
		for(Student std : studentList) {
			if(std.getName().equals(input)) { //이름이 일치하는 경우
				//일치하는 학생의 정보 출력
				System.out.println(std);
				flag = false;
			}
		}
		
		if (flag) { //flag가 true인 경우 == for문 내에 있는 if가 수행된 적 X
					// == 검색 결과가 없다.
			System.out.println("검색 결과가 없습니다.");
		}
		
	}
	
	/**
	 * 6. 이름에 특정 문자열이 포함되는 학생을 찾아서 조회하는 메소드 
	 */
	public void searchName2() {
		//contains: 포함
		//boolean String.contains(문자열): String에 문자열이 포함되어 있으면 true, 아니면 false
		
		System.out.println("=====학생 이름(문자열 포함)=====");
		
		System.out.print("이름에 포함되는 문자열 입력: ");
		String input = sc.next();
		
		boolean flag = true;
		//향상된 for문
		for(Student std : studentList) {
			if(std.getName().contains(input)) { //순서 바뀌면 안 됨!!!!!!!!!!!!
				System.out.println(std);
				flag = false;
			}
		}
		
		if (flag) {
			System.out.println("검색 결과가 없습니다.");
		}
		
	}

}

StudentRun

package edu.kh.collection.run;

import edu.kh.collection.model.service.StudentService;

public class StudentRun {
	
	public static void main(String[] args) {
		
		StudentService service = new StudentService();
		
		service.displayMenu();
		
//		service.ex();
		
	}

}
profile
개발 일지

0개의 댓글