개발 보안

배열만 잘 만들면 자원 절약, 코드 간결

아엠그라운드 2022. 4. 3. 17:00

배열

C#에서 배열은 참조형이기 때문에 스택이 아닌 힙 영역에 할당된다. 배열의 원소는 원소의 타입에 따라 달리 저장된다. , 원소의 타입이 값 형식인 경우는 배열에 직접 저장이 되며 참조 형식인 경우에는 배열에는 참조값만 저장한다. 배열의 선언 형식은 아래와 같다.

 

type[] arrayName;

 

위와 같이 선언하면 배열 객체가 생성되지 않기 때문에 arrayName에는 Null 값이 저장된다. 다른 객체 생성과 마찬가지로 new 연산자를 사용하여 배열 객체를 생성한 후 이를 지정해 주어야 한다.

 

double [] array;

array = new double[3];

 

배열이 생성되면 배열 요소에 맞는 기본값이 초기값으로 설정된다. 숫자 배열 요소에는 0, 참조 요소에는 null이 기본값으로 설정된다. 아래와 같이 배열 선언 및 생성과 함께 초기화할 수 있다.

 

Double [] array = new double[3] {1.0, 2.0, 3.0 } ;

 

초기화 시에 아래와 같이 new double[3] 부분을 생략할 수도 있다. 이 때 컴파일러는 초기화 값을 분석하여 배열의 크기를 결정하게 된다.

 

Double [] array = {1.0, 2.0, 3.0 }

 

배열 형식은 Array 추상 기본 형식에서 파생된 참조 형식이며 이 형식은 IEnumerable을 구현하므로 C#의 모든 배열에 foreach 반복을 사용할 수 있다. 아래의 예제 코드처럼 Main 메소드의 명령줄 인수를 통하여 프로그램 매개변수를 읽어드릴 수 있다. , C++와 달리 프로그램 이름은 첫 번째 명령줄 인수로 취급되지 않는다.

 

class Example3 {

static void Main(string[ ] args) {

foreach (string arg in args)

{

System.Console.WriteLine(arg);

}

}

}

System.ArrayArray 클래스는 배열을 지원하는 언어 구현의 기본 클래스로 시스템 및 컴파일러만 명시적으로 이 클래스로부터 다른 클래스를 파생시킬 수 있다. 사용자는 언어에서 제공되는 배열 구문을 사용해야 한다. Array 클래스는 배열을 만들고, 조작하고, 검색 및 정렬하여 공용 언어 런타임에서 모든 배열의 기본 클래스 역할을 수행하도록 하는 메서드를 제공하는데 그 중 대표적인 메소드 및 프로퍼티는 다음과 같다.참고로, 배열에 Sort 메소드를 적용시키면 배열 요소의 IComparable.CompareTo 메소드의 결과 값에 따라 정렬이 된다.

 

배열을 메소드의 인수로 넘길 때는 아래의 예제처럼 하면 된다.

 

void Test ()

{

double t = new int[3] {1, 2, 3};

 

ModifyArray( t );

for(int j=0; j < t.Length; j++) Console.Write("{0}", t[j]);

}

 

void ModifyArray( int[] b )

{

for (int j=0; j < b.Length; j++) b[j] *= 2;

b = new int[] {7, 8, 9};

}

 

배열 인수는 call-by-reference에 의해 배열 객체의 참조가 복사되어 전달이 된다. 그래서 ModifyArray 메소드 안에서 인수 b를 조작하면 hourlyTemperatures가 가리키는 배열 객체를 조작하게 되어 화면에 “1, 4, 9”를 출력하게 된다. 만약, 메소드의 선언을 아래와 같이 한다면 배열 변수가 가리키는 객체 자체가 변경되어 “7 8 9”를 출력하게 된다.

 

void ModifyArray( ref int[] b )

{

for (int j=0; j < b.Length; j++) b[j] *= 2;

b = new int[] {7, 8, 9};

}

 

다차원 배열은 아래 보는 바와 같이 선언하여 사용한다. 다차원 배열은 요소들을 사각형 모양의 테이블에 쓸 수 있기 때문에 사각형 배열이라고도 한다.

 

int [,] myArray2d;

myArray2d = new int[2,3] { {1, 0, 3 }, {6, 9, 12 } };

int [,,] myArray3d = new int[2,3,2];

 

int x = myArray3d[1,2,0] + myArray2d[0,1];

 

C#에는 다른 형태의 배열인 들쭉날쭉 (jagged) 배열을 제공한다. 이 배열은 배열의 요소로 배열이 사용되는 형태로 다양한 차원과 크기를 가질 수 있다. 들쭉날쭉 배열의 선언과 사용방법은 아래와 같다.

int [][] myArray2d = {new int[]{1, 0, 3}, new int[]{6, 9, 12}};

또는

int [][] myArray2d;

myArray2d = new int[2][];

myArray2d[0] = new int[3]{1, 0, 3};

myArray2d[1] = new int[3]{6, 9, 12};

 

위의 예제에서 다차원 배열이나 들쭉날쭉 배열이나 모두 23열 배열을 만들었다는 점에서는 동일하나 내부적으로 큰 차이가 있다. 아래 그림의 왼쪽 부분은 다차원 배열로 선언한 경우이고 오른쪽 부분은 들쭉날쭉 배열로 선언한 경우의 메모리 할당의 상태를 보여주고 있다. 보는 바와 같이 다차원 배열은 전체 배열을 저장하기 위한 하나의 메모리 덩어리를 할당 받게 되는 반면 들쭉날쭉 배열인 경우는 일차원 배열의 형태로 관리됨을 알 수 있다.

 

 

 

둘쭉날쭉 배열은 배열의 배열 형태이기 때문에 아래와 같이 지칭되는 배열의 크기를 달리 할 수 있다.

 

int[][] jagged = { new int[] {1, 2}, new int[] {3}, new int[] {4, 5, 6 } };

 

다차원 배열인 경우, 모든 요소에 대해서 반복 작업을 할 경우에는 일반적으로 아래와 같이 중첩 for문을 사용하면 된다. 여기서 GetLength 메소드는 각 차원의 원소의 개수를 돌려주는 메소드이다.

 

for (int row = 0; row < array.GetLength(0); row++)

{

for (int col = 0; col < array.GetLength(1); col++)

{

...

}

}

 

하지만 들쭉날쭉 배열인 경우는 행마다 열의 크기가 달라질 수 있기 때문에 아래처럼 처리해야 한다.

 

for (int row = 0; row < array.Length; row++)

{

for (int col = 0; col < array[row].Length; col++)

{

...

}

}

C#에서 배열은 참조형이기 때문에 스택이 아닌 힙 영역에 할당된다. 배열의 원소는 원소의 타입에 따라 달리 저장된다. , 원소의 타입이 값 형식인 경우는 배열에 직접 저장이 되며 참조 형식인 경우에는 배열에는 참조값만 저장한다. 배열의 선언 형식은 아래와 같다.

 

type[] arrayName;

 

위와 같이 선언하면 배열 객체가 생성되지 않기 때문에 arrayName에는 Null 값이 저장된다. 다른 객체 생성과 마찬가지로 new 연산자를 사용하여 배열 객체를 생성한 후 이를 지정해 주어야 한다.

 

double [] array;

array = new double[3];

 

배열이 생성되면 배열 요소에 맞는 기본값이 초기값으로 설정된다. 숫자 배열 요소에는 0, 참조 요소에는 null이 기본값으로 설정된다. 아래와 같이 배열 선언 및 생성과 함께 초기화할 수 있다.

 

Double [] array = new double[3] {1.0, 2.0, 3.0 } ;

 

초기화 시에 아래와 같이 new double[3] 부분을 생략할 수도 있다. 이 때 컴파일러는 초기화 값을 분석하여 배열의 크기를 결정하게 된다.

 

Double [] array = {1.0, 2.0, 3.0 }

 

배열 형식은 Array 추상 기본 형식에서 파생된 참조 형식이며 이 형식은 IEnumerable을 구현하므로 C#의 모든 배열에 foreach 반복을 사용할 수 있다. 아래의 예제 코드처럼 Main 메소드의 명령줄 인수를 통하여 프로그램 매개변수를 읽어드릴 수 있다. , C++와 달리 프로그램 이름은 첫 번째 명령줄 인수로 취급되지 않는다.

 

class Example3 {

static void Main(string[ ] args) {

foreach (string arg in args)

{

System.Console.WriteLine(arg);

}

}

}

System.ArrayArray 클래스는 배열을 지원하는 언어 구현의 기본 클래스로 시스템 및 컴파일러만 명시적으로 이 클래스로부터 다른 클래스를 파생시킬 수 있다. 사용자는 언어에서 제공되는 배열 구문을 사용해야 한다. Array 클래스는 배열을 만들고, 조작하고, 검색 및 정렬하여 공용 언어 런타임에서 모든 배열의 기본 클래스 역할을 수행하도록 하는 메서드를 제공하는데 그 중 대표적인 메소드 및 프로퍼티는 다음과 같다.참고로, 배열에 Sort 메소드를 적용시키면 배열 요소의 IComparable.CompareTo 메소드의 결과 값에 따라 정렬이 된다.

 

배열을 메소드의 인수로 넘길 때는 아래의 예제처럼 하면 된다.

 

void Test ()

{

double t = new int[3] {1, 2, 3};

 

ModifyArray( t );

for(int j=0; j < t.Length; j++) Console.Write("{0}", t[j]);

}

 

void ModifyArray( int[] b )

{

for (int j=0; j < b.Length; j++) b[j] *= 2;

b = new int[] {7, 8, 9};

}

 

배열 인수는 call-by-reference에 의해 배열 객체의 참조가 복사되어 전달이 된다. 그래서 ModifyArray 메소드 안에서 인수 b를 조작하면 hourlyTemperatures가 가리키는 배열 객체를 조작하게 되어 화면에 “1, 4, 9”를 출력하게 된다. 만약, 메소드의 선언을 아래와 같이 한다면 배열 변수가 가리키는 객체 자체가 변경되어 “7 8 9”를 출력하게 된다.

 

void ModifyArray( ref int[] b )

{

for (int j=0; j < b.Length; j++) b[j] *= 2;

b = new int[] {7, 8, 9};

}

 

다차원 배열은 아래 보는 바와 같이 선언하여 사용한다. 다차원 배열은 요소들을 사각형 모양의 테이블에 쓸 수 있기 때문에 사각형 배열이라고도 한다.

 

int [,] myArray2d;

myArray2d = new int[2,3] { {1, 0, 3 }, {6, 9, 12 } };

int [,,] myArray3d = new int[2,3,2];

 

int x = myArray3d[1,2,0] + myArray2d[0,1];

 

C#에는 다른 형태의 배열인 들쭉날쭉 (jagged) 배열을 제공한다. 이 배열은 배열의 요소로 배열이 사용되는 형태로 다양한 차원과 크기를 가질 수 있다. 들쭉날쭉 배열의 선언과 사용방법은 아래와 같다.

int [][] myArray2d = {new int[]{1, 0, 3}, new int[]{6, 9, 12}};

또는

int [][] myArray2d;

myArray2d = new int[2][];

myArray2d[0] = new int[3]{1, 0, 3};

myArray2d[1] = new int[3]{6, 9, 12};

 

위의 예제에서 다차원 배열이나 들쭉날쭉 배열이나 모두 23열 배열을 만들었다는 점에서는 동일하나 내부적으로 큰 차이가 있다. 아래 그림의 왼쪽 부분은 다차원 배열로 선언한 경우이고 오른쪽 부분은 들쭉날쭉 배열로 선언한 경우의 메모리 할당의 상태를 보여주고 있다. 보는 바와 같이 다차원 배열은 전체 배열을 저장하기 위한 하나의 메모리 덩어리를 할당 받게 되는 반면 들쭉날쭉 배열인 경우는 일차원 배열의 형태로 관리됨을 알 수 있다.

 

 

 

둘쭉날쭉 배열은 배열의 배열 형태이기 때문에 아래와 같이 지칭되는 배열의 크기를 달리 할 수 있다.

 

int[][] jagged = { new int[] {1, 2}, new int[] {3}, new int[] {4, 5, 6 } };

 

다차원 배열인 경우, 모든 요소에 대해서 반복 작업을 할 경우에는 일반적으로 아래와 같이 중첩 for문을 사용하면 된다. 여기서 GetLength 메소드는 각 차원의 원소의 개수를 돌려주는 메소드이다.

 

for (int row = 0; row < array.GetLength(0); row++)

{

for (int col = 0; col < array.GetLength(1); col++)

{

...

}

}

 

하지만 들쭉날쭉 배열인 경우는 행마다 열의 크기가 달라질 수 있기 때문에 아래처럼 처리해야 한다.

 

for (int row = 0; row < array.Length; row++)

{

for (int col = 0; col < array[row].Length; col++)

{

...

}

}

C#에서 배열은 참조형이기 때문에 스택이 아닌 힙 영역에 할당된다. 배열의 원소는 원소의 타입에 따라 달리 저장된다. , 원소의 타입이 값 형식인 경우는 배열에 직접 저장이 되며 참조 형식인 경우에는 배열에는 참조값만 저장한다. 배열의 선언 형식은 아래와 같다.

 

type[] arrayName;

 

위와 같이 선언하면 배열 객체가 생성되지 않기 때문에 arrayName에는 Null 값이 저장된다. 다른 객체 생성과 마찬가지로 new 연산자를 사용하여 배열 객체를 생성한 후 이를 지정해 주어야 한다.

 

double [] array;

array = new double[3];

 

배열이 생성되면 배열 요소에 맞는 기본값이 초기값으로 설정된다. 숫자 배열 요소에는 0, 참조 요소에는 null이 기본값으로 설정된다. 아래와 같이 배열 선언 및 생성과 함께 초기화할 수 있다.

 

Double [] array = new double[3] {1.0, 2.0, 3.0 } ;

 

초기화 시에 아래와 같이 new double[3] 부분을 생략할 수도 있다. 이 때 컴파일러는 초기화 값을 분석하여 배열의 크기를 결정하게 된다.

 

Double [] array = {1.0, 2.0, 3.0 }

 

배열 형식은 Array 추상 기본 형식에서 파생된 참조 형식이며 이 형식은 IEnumerable을 구현하므로 C#의 모든 배열에 foreach 반복을 사용할 수 있다. 아래의 예제 코드처럼 Main 메소드의 명령줄 인수를 통하여 프로그램 매개변수를 읽어드릴 수 있다. , C++와 달리 프로그램 이름은 첫 번째 명령줄 인수로 취급되지 않는다.

 

class Example3 {

static void Main(string[ ] args) {

foreach (string arg in args)

{

System.Console.WriteLine(arg);

}

}

}

System.ArrayArray 클래스는 배열을 지원하는 언어 구현의 기본 클래스로 시스템 및 컴파일러만 명시적으로 이 클래스로부터 다른 클래스를 파생시킬 수 있다. 사용자는 언어에서 제공되는 배열 구문을 사용해야 한다. Array 클래스는 배열을 만들고, 조작하고, 검색 및 정렬하여 공용 언어 런타임에서 모든 배열의 기본 클래스 역할을 수행하도록 하는 메서드를 제공하는데 그 중 대표적인 메소드 및 프로퍼티는 다음과 같다.참고로, 배열에 Sort 메소드를 적용시키면 배열 요소의 IComparable.CompareTo 메소드의 결과 값에 따라 정렬이 된다.

 

배열을 메소드의 인수로 넘길 때는 아래의 예제처럼 하면 된다.

 

void Test ()

{

double t = new int[3] {1, 2, 3};

 

ModifyArray( t );

for(int j=0; j < t.Length; j++) Console.Write("{0}", t[j]);

}

 

void ModifyArray( int[] b )

{

for (int j=0; j < b.Length; j++) b[j] *= 2;

b = new int[] {7, 8, 9};

}

 

배열 인수는 call-by-reference에 의해 배열 객체의 참조가 복사되어 전달이 된다. 그래서 ModifyArray 메소드 안에서 인수 b를 조작하면 hourlyTemperatures가 가리키는 배열 객체를 조작하게 되어 화면에 “1, 4, 9”를 출력하게 된다. 만약, 메소드의 선언을 아래와 같이 한다면 배열 변수가 가리키는 객체 자체가 변경되어 “7 8 9”를 출력하게 된다.

 

void ModifyArray( ref int[] b )

{

for (int j=0; j < b.Length; j++) b[j] *= 2;

b = new int[] {7, 8, 9};

}

 

다차원 배열은 아래 보는 바와 같이 선언하여 사용한다. 다차원 배열은 요소들을 사각형 모양의 테이블에 쓸 수 있기 때문에 사각형 배열이라고도 한다.

 

int [,] myArray2d;

myArray2d = new int[2,3] { {1, 0, 3 }, {6, 9, 12 } };

int [,,] myArray3d = new int[2,3,2];

 

int x = myArray3d[1,2,0] + myArray2d[0,1];

 

C#에는 다른 형태의 배열인 들쭉날쭉 (jagged) 배열을 제공한다. 이 배열은 배열의 요소로 배열이 사용되는 형태로 다양한 차원과 크기를 가질 수 있다. 들쭉날쭉 배열의 선언과 사용방법은 아래와 같다.

int [][] myArray2d = {new int[]{1, 0, 3}, new int[]{6, 9, 12}};

또는

int [][] myArray2d;

myArray2d = new int[2][];

myArray2d[0] = new int[3]{1, 0, 3};

myArray2d[1] = new int[3]{6, 9, 12};

 

위의 예제에서 다차원 배열이나 들쭉날쭉 배열이나 모두 23열 배열을 만들었다는 점에서는 동일하나 내부적으로 큰 차이가 있다. 아래 그림의 왼쪽 부분은 다차원 배열로 선언한 경우이고 오른쪽 부분은 들쭉날쭉 배열로 선언한 경우의 메모리 할당의 상태를 보여주고 있다. 보는 바와 같이 다차원 배열은 전체 배열을 저장하기 위한 하나의 메모리 덩어리를 할당 받게 되는 반면 들쭉날쭉 배열인 경우는 일차원 배열의 형태로 관리됨을 알 수 있다.

 

 

 

둘쭉날쭉 배열은 배열의 배열 형태이기 때문에 아래와 같이 지칭되는 배열의 크기를 달리 할 수 있다.

 

int[][] jagged = { new int[] {1, 2}, new int[] {3}, new int[] {4, 5, 6 } };

 

다차원 배열인 경우, 모든 요소에 대해서 반복 작업을 할 경우에는 일반적으로 아래와 같이 중첩 for문을 사용하면 된다. 여기서 GetLength 메소드는 각 차원의 원소의 개수를 돌려주는 메소드이다.

 

for (int row = 0; row < array.GetLength(0); row++)

{

for (int col = 0; col < array.GetLength(1); col++)

{

...

}

}

 

하지만 들쭉날쭉 배열인 경우는 행마다 열의 크기가 달라질 수 있기 때문에 아래처럼 처리해야 한다.

 

for (int row = 0; row < array.Length; row++)

{

for (int col = 0; col < array[row].Length; col++)

{

...

}

}