2022.08.12 경일 메타버스 19주차 5일 수업내용. 배열과 컬렉션 그리고 인덱서(자습)
p. 357 ~ 359
같은 성격(타입)을 띈 다수의 데이터를 한번에 다뤄야 하는 경우에 사용
형식
데이터형식[] 배열이름 = new 데이터형식[용량];
배열의 요소에 접근(데이터를 저장, 데이터를 조회)할 때는 배열 이름 뒤에 괄호[]를 붙이고, 괄호 사이에 인덱스(index)를 적는다.
같은 성격의 데이터라면 변수를 여러 개 사용하기 보다
배열로 정의한 다음 for문 혹은 foreach문과 함께 사용하는 것이
코드를 보다 간결하게 만든다.
배열을 사용하면 유지보수가 쉽다.
p. 360 ~ 361
컬렉션의 마지막부터 역순으로 인덱스를 지정
ex.
arr[^1] = 34; // arr[arr.Length - 1] = 34; 와 동일
배열의 원소 개수를 명시하고, 중괄호 {}로 구분된 블록을 붙인 뒤 블록 사이에 배열의 각 원소에 입력될 데이터를 입력
객체를 초기화하는 {} 블록 : 컬렉션 초기자 (Collection Initializer)
ex.
string[] array1 = new string[3] { “안녕”, “Hello”, “Halo” };
첫 번째 방법에서 배열의 용량을 생략
ex.
string[] array2 = new string[] { “안녕”, “Hello”, “Halo” };
첫 번째 방법에서 우변의 컬렉션 초기자와 그 안 데이터를 제외하고 new 연산자, 형식, 대괄호, 배열의 용량을 모두 생략
ex.
string[] array3 = { “안녕”, “Hello”, “Halo” };
p. 365 ~ 366
C#에서 배열은 System.Array 클래스에 대응된다.
Array 클래스의 주요 메소드 / 프로퍼티
분류 | 이름 | 설명 |
---|---|---|
정적 메소드 | void Sort() | 배열을 정렬 |
int BinarySearch() | 이진 탐색을 수행 | |
int IndexOf() | 찾고자 하는 특정 데이터의 인덱스를 반환 | |
bool TrueForAll() | 모든 요소가 지정 조건에 부합하는지 여부를 반환 | |
int FindIndex() | 지정 조건에 부합하는 첫 번째 요소의 인덱스를 반환 | |
void Resize() | 배열의 크기 재조정 | |
void Clear() | 모든 요소 초기화 | |
숫자 형식 : 0 | ||
논리 형식 : false | ||
참조 형식 : null | ||
void ForEach() | 모든 요소에 대해 동일 작업 수행 | |
void Copy() | 배열의 일부를 다른 배열에 복사 | |
인스턴스 메소드 | int GetLength() | 지정한 차원의 길이 반환 |
프로퍼티 | Length | 배열의 길이 반환, int |
Rank | 배열의 차원 수 반환, int |
p. 369 ~ 370
분할(Slice) :
배열의 일부를 다른 곳에 복사하는 것
System.Range
시작 인덱스와 마지막 인덱스를 이용해 범위를 나타냄
.. 연산자
왼쪽 - 시작 .. 오른쪽 - 마지막
ex.
int[] sliced = scores[0..3];
마지막 인덱스는 범위에서 제외된다.
두 인덱스는 생략 가능
시작 생략 : 시작 인덱스 = 배열 첫 번째 요소의 위치
마지막 생략 : 마지막 인덱스 = 배열 마지막 요소의 위치
p. 372 ~ 373
2개의 차원(가로세로)으로 원소를 배치하는 배열
1차원 배열을 원소로 갖는 배열
형식 : 차원의 용량을 콤마 ,로 구분
데이터형식[,] 배열이름 = new 데이터형식[2차원길이, 1차원길이];
접근 : 두 차원의 인덱스를 괄호 사이에 입력
배열이름[2차원인덱스, 1차원인덱스];
초기화 : 1차원의 경우와 같다.
다차원 배열 :
차원이 둘 이상인 배열. 형식은 비슷하다. 내용을 떠올리기 쉽지 않기에 디버깅이 힘들다.
p. 378 ~ 379
다양한 길이의 배열을 요소로 갖는 다차원 배열
길이를 변하게 할 수 있다고 이해하기 보단,
들쭉날쭉한 배열이라고 이해하면 좋다.
배열을 요소로 사용해 접근 가능
선언 형식 : []가 두 개
데이터형식[][] 배열이름 = new 데이터형식[가변 배열의 용량][];
ex.
int[][] jagged = new int[3][];
jagged[0] = new int[5] {1, 2, 3, 4, 5};
jagged[1] = new int[] {10, 20, 30};
jagged[2] = new int[] {100, 200};
가변 배열의 요소인 배열은 그 길이가 모두 달라도 좋다.
⇒ Jagged 배열
초기화 : 가변 배열은 2차원 배열과 다르게 초기화가 이루어진다.
int[][] jagged2 = new int[2][] { new int[] {1000, 2000}, new int[4] {6, 7, 8, 9} };
p. 380 ~ 392
컬렉션 :
같은 성격(타입)을 띈 데이터의 모음을 담는 자료구조
.NET이 제공하는 컬렉션은 ICollection 인터페이스를 상속한다.
책에서 다루는 컬렉션
Array
ArrayList
Queue
Stack
Hashtable
p. 381 ~ 382
배열과 닮은 컬렉션
접근 : [] 연산자
특정 위치 요소에 데이터 임의 할당 가능
용량이 필요에 따라 변한다.
주요 메소드
Add()
가장 마지막에 있는 요소 뒤에 새 요소 추가
RemoveAt()
특정 위치(인덱스)의 요소 제거
Insert()
원하는 위치(특정 위치, 인덱스)에 새 요소 삽입
p. 384
데이터, 작업을 차례대로 입력해두고 입력된 순서대로 하나씩 꺼내 처리
선입선출, FIFO
입력은 뒤, 출력은 앞에서만 이루어진다.
주요 메소드
Enqueue()
뒤에서 데이터 입력
Dequeue()
앞에서 데이터 출력과 함께 데이터 삭제
p. 386
나중에 입력된 데이터를 먼저 출력
후입선출, LIFO
주요 메소드
Push()
앞에 데이터를 입력
데이터를 위에 쌓는다.
Pop()
앞의 데이터를 출력, 삭제
데이터를 꺼낸다.
p. 387 ~ 388
키(Key)와 값(Value)의 쌍으로 이루어진 데이터를 다룬다.
값을 키와 묶어 저장한다.
배열과 비슷하지만, 배열과 달리 요소에 키로 접근한다.
장점
편의성
어떤 형식이든 키로 사용할 수 있다.
빠른 탐색 속도
키를 이용, 키와 쌍을 이루는 값(데이터)의 주소를 바로 계산할 수 있다.
해싱(Hashing)
p. 389 ~ 392
ArrayList, Queue, Stack은 생성자를 호출할 때 배열 객체를 매개변수로 넘겨 초기화할 수 있다.
이때 컬렉션 객체는 배열 객체의 데이터로 내부 데이터를 채운다.
ex.
int[] arr = {123, 456, 789};
ArrayList list = new ArrayList(arr); // 123, 456, 789
Stack stack = new Stack(arr); // 789, 456, 123
Queue queue = new Queue(arr); // 123, 456, 789
ArrayList, Hashtable은 컬렉션 초기자를 이용해 초기화할 수 있다.
ex.
ArrayList list2 = new ArrayList() {11, 22, 33};
Hashtable ht = new Hashtable()
{
{"하나", 1},
{"둘", 2},
{"셋", 3}
};
컬렉션 초기자는 IEnumerable 인터페이스와 Add() 메소드를 구현하는 컬렉션만 지원
⇒ Stack, Queue은 IEnumerable을 상속하지만 Add() 메소드는 구현하지 않는다.
⇒ Stack, Queue는 컬렉션 초기자를 이용할 수 없다.
Hashtable은 딕셔너리 초기자 (Dictionary Initializer)를 이용해 초기화할 수 있다.
ex.
Hashtable ht2 = new Hashtable()
{
["하나"] = 1,
["둘"] = 2,
["셋"] = 3
};
p. 392 ~ 394
인덱스를 이용해 객체 내의 데이터에 접근하게 해주는 프로퍼티
프로퍼티 : 객체 내의 데이터에 접근할 수 있도록 하는 통로
객체를 배열처럼 사용할 수 있다.
인덱서는 식별자를 갖지 않는다.
식별자가 아닌 인덱스를 통해 데이터에 접근
p. 396 ~ 400
foreach 문 :
객체 내의 요소를 순회하는 반복문
컬렉션에만 사용 가능
IEnumerable을 상속하는 형식만 지원
주요 메소드
yield 문 이용
컴파일러가 해당 인터페이스를 구현한 클래스를 생성
주요 메소드
boolean MoveNext() :
다음 요소로 이동
컬렉션의 끝을 지나면 false, 지나지 않고 이동이 성공하면 true
void Reset() :
컬렉션 첫 번째 위치의 앞으로 이동
Object Current { get; } :
컬렉션의 현재 요소 반환