달나라 노트

C# : array 본문

C#/C#

C# : array

CosmosProject 2022. 3. 23. 20:23
728x90
반응형

 

 

 

Array는 여러 값들을 하나로 묶어놓은 것을 의미합니다.

Python의 list와 비슷한 개념입니다.

 

string[] test_arr = { "Apple", "Banana", "Pineapple" };

array의 생성은 위처럼 할 수 있습니다.

 

string[] -> Array에 들어갈 요소들의 자료형입니다.

test_arr -> Array의 이름입니다.

{ "Apple", "Banana", "Pineapple" } -> Array의 요소입니다.

 

 

 

 

int[] test_arr = { 1, 2, 3, 4, 5 };

정수 요소들을 담은 array입니다.

 

 

 

 

 

using System;

class MyProgram
{
    static void Main()
    {
        string[] test_arr = { "Apple", "Banana", "Pineapple" };

        Console.WriteLine(test_arr[0]);
        Console.WriteLine(test_arr[1]);
        Console.WriteLine(test_arr[2]);
    }
}


-- Result
Apple
Banana
Pineapple

indexing을 해서 array 속 어떤 요소를 얻을 수 있습니다.

 

 

 

 

 

using System;

class MyProgram
{
    static void Main()
    {
        string[] test_arr = { "Apple", "Banana", "Pineapple" };

        Console.WriteLine(test_arr[1]);

        test_arr[1] = "Grape";

        Console.WriteLine(test_arr[1]);
    }
}


-- Result
Banana
Grape

indexing을 이용하면 특정 index의 위치에 있는 요소의 값을 바꿀 수 있습니다.

 

 

 

 

 

using System;

class MyProgram
{
    static void Main()
    {
        string[] test_arr = { "Apple", "Banana", "Pineapple" };

        Console.WriteLine(test_arr.Length);
    }
}


-- Result
3

Length를 이용하면 array의 길이를 얻을 수 있습니다.

 

 

 

 

 

string[] test_arr1 = new string[3];
string[] test_arr3 = new string[3] { "Apple", "Banana", "Pineapple" };
string[] test_arr4 = new string[] { "Apple", "Banana", "Pineapple" };

위 예시는 array를 선언하는 다양한 방법을 나타낸겁니다.

 

string[] test_arr1 = new string[3];

길이가 3인 비어있는 array를 선언해두고 나중에 할당하기 위한 array입니다.

여기서 한가지 주의할 것은 비어있는 array를 선언할 때에는 반드시 new string[3] 처럼 미리 array의 길이를 지정해야 한다는 것입니다.

비어있는 array 선언 시 array의 길이를 명시하지 않으면 에러가 발생합니다.

만약 길이를 지정하지 않은 채로 비어있는 collection을 선언하고싶으면 array 대신 list를 사용해야합니다.

 

https://cosmosproject.tistory.com/574

 

C# : List

C#에서 여러 요소를 하나의 묶음으로 저장할 수 있는 대표적인 자료형은 Array입니다. Array 관련 내용 = https://cosmosproject.tistory.com/539 Arra.." data-og-host="cosmosproject.tistory.com" data-og-sou..

cosmosproject.tistory.com

 

 

 

 

string[] test_arr3 = new string[3] { "Apple", "Banana", "Pineapple" };

길이가 3인 array를 선언하고 { "Apple", "Banana", "Pineapple" } 로 채웁니다.

이렇게 길이를 지정하여 array를 선언하면 array는 그 길이를 넘어설 수 없습니다.

 

예를들어 위 array는 총 3개의 요소만 담을 수 있는 array이므로, index = 3에 네 번 째 요소를 삽입하려하거나 조회하려하면 에러가 발생합니다.

 

 

string[] test_arr4 = new string[] { "Apple", "Banana", "Pineapple" };

길이를 별도로 지정하지 않고 array를 선언합니다.

이런 경우 내가 원하는 만큼의 요소를 추가할 수 있습니다.

단, 주의할 점은 길이를 별도로 지정하지 않은 array는 단순히 처음 할당하는 array의 길이로 고정이됩니다.

즉, 처음에는 내가 원하는 길이의 array를 할당할 수 있지만, 한 번 할당한 후에는 처음에 할당한 요소들의 개수보다 더 많은 요소를 할당할 수 없습니다.

 

예를들어 위 예시는 Apple, Banana, Pineapple 이라는 총 3개의 요소를 가진 array로 초기화되었으므로, index = 3, index = 4, ... 등에 추가로 요소를 삽입할 수 없습니다.

 

 

 

 

 

 

 

 


 

 

 

 

 

지금까지는 보았던 array는 1차원 array입니다.

그러나 C#에서도 Python numpy의 다차원 array처럼 다차원 array를 지원합니다.

 

다차원 array는 array속에 또다른 array가 존재하는 형태라고 생각하면 됩니다.

 

 

아래 예시는 다차원 array를 선언하는 예시입니다.

 

string[,] test_arr = new string[4, 3]
{
    {"과일", "Apple", "사과"},
    {"과일", "Peach", "복숭아"},
    {"야채", "Potato", "감자"},
    {"야채", "Carrot", "당근"}
};

위 예시는 2차원 array입니다. array속에 또 다른 array가 있기 때문이죠.

 

- string[,] test_arr = new string[4, 3]

먼저 다차원 array 선언부분입니다.

string[,] test_arr 이 부분을 봅시다. 이 부분은 test_arr라는 변수를 string[,]라는 타입으로 생성하겠다는 의미입니다.

여기서 string[,]의 의미는 string 타입의 데이터가 들어가는 2차원 array를 의미합니다.

2차원 array는 array 속에 또다른 내부 array가 있기 때문에 indexing을 할 때 2개의 index가 필요합니다.

따라서 콤마를 적어줌으로써 2차원이라는 내용을 명시해주는 것이죠.

(차원의 차수와 indexing에 필요한 index의 개수는 동일합니다.)

 

- new string[4, 3]

이 부분은 생성할 2차원 array의 크기와 타입을 지정해줍니다.

new 키워드는 array 뿐 아니라 class등 새로운 무언가를 생성할 때 사용하는 키워드입니다.

string[4, 3]은 string 타입의 데이터로 채워진 내부 array가 4개 있으며, 각각의 내부 array는 3개의 요소를 가지고있다는 의미입니다.

 

string[,] test_arr = new string[4, 3]
{
    {"과일", "Apple", "사과"},
    {"과일", "Peach", "복숭아"},
    {"야채", "Potato", "감자"},
    {"야채", "Carrot", "당근"}
};

위 array의 내용 부분을 봅시다.

 

보면 가장 바깥 쪽 array가 존재하고 그 안에 4개의 내부 array가 있습니다.

그리고 각각의 내부 array에는 3개의 요소가 있습니다.

 

2차원 array를 직관적으로 이해하는 좋은 방법은 위 형태를 아래처럼 엑셀에 그대로 붙여넣었다고 생각하는 겁니다.

과일 Apple 사과
과일 Peach 복숭아
야채 Potato 감자
야채 Carrot 당근

마치 4행 3열의 데이터처럼 생각하면 2차원 array를 다룰 때 굉장히 쉬워집니다.

 

 

using System;

class MyProgram
{
    static void Main()
    {
        string[,] test_arr = new string[4, 3]
        {
            {"과일", "Apple", "사과"},
            {"과일", "Peach", "복숭아"},
            {"야채", "Potato", "감자"},
            {"야채", "Carrot", "당근"}
        };

        Console.WriteLine(test_arr[0, 0]);
        Console.WriteLine(test_arr[0, 1]);
        Console.WriteLine(test_arr[0, 2]);

        Console.WriteLine(test_arr[1, 0]);
        Console.WriteLine(test_arr[1, 1]);
        Console.WriteLine(test_arr[1, 2]);

        Console.WriteLine(test_arr[2, 0]);
        Console.WriteLine(test_arr[2, 1]);
        Console.WriteLine(test_arr[2, 2]);

        Console.WriteLine(test_arr[3, 0]);
        Console.WriteLine(test_arr[3, 1]);
        Console.WriteLine(test_arr[3, 2]);
    }
}


-- Result
과일
Apple
사과

과일
Peach
복숭아

야채
Potato
감자

야채
Carrot
당근

다차원 array의 indexing은 가장 바깥쪽 array부터 indexing을 하기 시작합니다.

test_arr[2, 1]의 의미는 다음과 같습니다.

2 -> 가장 바깥쪽 array에 포함된 4개의 내부 array중 index = 2 위치의 내부 array를 불러와라

1 -> index = 2 위치에 있는 내부 array의 요소 중 index = 1 위치의 요소를 불러와라.

 

이렇게 2차원 array의 indexing을 좀 더 쉽게 직관적으로 이해하는 방법은 test_arr[2, 1][행 index, 열 index]의 형태로 명시했다고 생각하면 편합니다.

(주의할점은 3차원 이상의 array로 가면 위 방법은 사용하기 어려우니 2차원 array에 한해서만 생각하도록 합시다.)

 

 

 

 

 

using System;

class MyProgram
{
    static void Main()
    {
        string[,,] test_arr = new string[2, 3, 2]
        {
            {
                {"a", "A"},
                {"b", "B"},
                {"c", "C"}
            },
            {
                {"d", "D"},
                {"e", "E"},
                {"f", "F"}
            }
        };

        Console.WriteLine(test_arr[0, 0, 0]);
        Console.WriteLine(test_arr[0, 0, 1]);

        Console.WriteLine(test_arr[0, 1, 0]);
        Console.WriteLine(test_arr[0, 1, 1]);

        Console.WriteLine(test_arr[0, 2, 0]);
        Console.WriteLine(test_arr[0, 2, 1]);

        Console.WriteLine(test_arr[1, 0, 0]);
        Console.WriteLine(test_arr[1, 0, 1]);

        Console.WriteLine(test_arr[1, 1, 0]);
        Console.WriteLine(test_arr[1, 1, 1]);

        Console.WriteLine(test_arr[1, 2, 0]);
        Console.WriteLine(test_arr[1, 2, 1]);
    }
}


-- Result
a
A
b
B
c
C
d
D
e
E
f
F

위 예시는 3차원 array의 선언입니다.

맥락은 2차원 array의 선언과 비슷합니다.

 

string[,,] test_arr = new string[2, 3, 2]

좀 변한 부분을 살펴봅시다.

 

- string[,,] test_arr

3차원 array는 array 속 array 속 요소들이 존재하는 형태입니다.

따라서 3차원 array의 indexing을 위해선 총 3개의 index가 필요합니다. (차원의 차수와 indexing에 필요한 index의 개수는 동일합니다.)

따라서 콤마를 2개 적어줌으로써 indexing에 3개의 index가 필요한 3차원 array라는 것을 명시해주는 부분입니다.

 

- new string[2, 3, 2]

3차원 array의 크기를 선언하는 부분입니다.

대괄호 안에 있는 숫자는 다음과 같은 의미를 가집니다.

2 -> 가장 바깥 쪽 array는 2개의 내부 array(1차 내부 array)를 가집니다.

3 -> 내부 array(1차 내부 array)는 또 다시 3개의 내부 array(2차 내부 array)를 가집니다.

2 -> 내부 array(2차 내부 array)는 각각 2개의 요소를 가집니다.

 

 

위 예시는 3차원 array이기 때문에 indexing에도 최대 개의 index가 필요한 것을 알 수 있습니다.

 

 

 

 

 

 

지금까지 다차원 array를 생성할 때에는 다차원 array의 길이를 명시해주었습니다.

그런데 항상 길이를 명시해주는건 좀 번거로울 수 있겠죠.

 

그래서 이를 대체할 방법인 가변 배열(Jagged array, 재그 배열)이라는 것이 있습니다.

개념은 간단합니다. 그냥 다차원 array의 길이를 알려주지 않고 내가 원하는 길이의 array를 선언하는 것입니다.

 

아래 예시를 보시죠.

 

string[][] test_arr = new string[][]
{
    new string[] {"A", "B", "C"},
    new string[] {"D", "E"},
    new string[] {"F"}
};

2차원 가변 배열의 선언입니다.

 

크기를 정해둔 2차원 배열의 선언과는 조금 차이가 있죠.

 

- string[][] test_arr = new string[][]

일단 2차원 array이기 때문에 indexing이 최대 2개가 필요합니다.

하지만 그 크기를 미리 정하지 않겠다는 의미로 대괄호 2쌍을 사용한 것입니다.

 

 

{
    new string[] {"A", "B", "C"},
    new string[] {"D", "E"},
    new string[] {"F"}
};

array의 내용에도 약간의 차이가 있습니다.

가장 외부 array 속에 3개의 내부 array가 있습니다.

그리고 각각의 내부 array는 모두 new string[] 키워드와 함께 선언됩니다.

이렇게 선언한 이유는 각각의 내부 array가 가진 요소들의 개수도 모르기에 new string[] 처럼 비어있는 대괄호로 명시한 것입니다.

 

 

 

 

using System;

class MyProgram
{
    static void Main()
    {
        string[][] test_arr = new string[][]
        {
            new string[] {"A", "B", "C"},
            new string[] {"D", "E"},
            new string[] {"F"}
        };

        Console.WriteLine(test_arr[0][0]);
        Console.WriteLine(test_arr[0][1]);
        Console.WriteLine(test_arr[0][2]);

        Console.WriteLine(test_arr[1][0]);
        Console.WriteLine(test_arr[1][1]);

        Console.WriteLine(test_arr[2][0]);
    }
}


-- Result
A
B
C
D
E
F

가변 array의 indexing은 콤마가 아닌 대괄호 2개를 연달아서 이용한다는 것에 주의합시다.

 

 

 

 

using System;

class MyProgram
{
    static void Main()
    {
        string[][] test_arr = new string[][]
        {
            new string[] {"A", "a"},
            new string[] {"B", "b"},
            new string[] {"C", "c"},
            new string[] {"D", "d", "E", "e"},
        };

        Console.WriteLine(test_arr[0][0]);

        test_arr[0][0] = "Apple";
        Console.WriteLine(test_arr[0][0]);
    }
}


-- Result
A
Apple

가변 array도 마찬가지로 indexing을 이용해서 특정 위치에 있는 요소의 값을 변경할 수 있습니다.

 

 

 

 

 

 

using System;

class MyProgram
{
    static void Main()
    {
        string[][] test_arr = new string[][]
        {
            new string[] {"A", "a"},
            new string[] {"B", "b"},
            new string[] {"C", "c"},
            new string[] {"D", "d", "E", "e"},
        };
        
        test_arr[0] = new string[] { "Z", "z", "X", "x" };
        for (int i = 0; i < test_arr.Length; i++)
        {
            for (int j = 0; j < test_arr[i].Length; j++)
            {
                Console.WriteLine(test_arr[i][j]);
            }
        }
    }
}


-- Result
Z
z
X
x
B
b
C
c
D
d
E
e

단순히 어떤 위치의 요소 뿐 아니라

특정 위치에 있는 내부 array 전체를 변경할 수도 있습니다.

 

 

...
        string[][] test_arr = new string[][]
        {
            new string[] {"A", "a"},
            new string[] {"B", "b"},
            new string[] {"C", "c"},
            new string[] {"D", "d", "E", "e"},
        };
        
        test_arr[0] = new string[] { "Z", "z", "X", "x" };
...

보면 원래 test_arr[0] 은 {"A", "a"} 입니다.

 

test_arr[0] = new string[] { "Z", "z", "X", "x" };

그런데 이 부분에서 test[0] 위치에 있는 내부 array 인 {"A", "a"} 자체를 { "Z", "z", "X", "x" } 이러한 array로 바꾸고 있습니다.

 

 

 

 

 

 

 


 

 

 

 

 

 

이번엔 위에서 본 array들을 반복문에 적용시켜봅시다.

 

using System;

class MyProgram
{
    static void Main()
    {
        string[][] test_arr = new string[][]
        {
            new string[] {"A", "B", "C"},
            new string[] {"D", "E"},
            new string[] {"F"}
        };

        for (int i = 0; i < test_arr.Length; i = i + 1)
        {
            for (int j = 0; j < test_arr[i].Length; j = j + 1)
            {
                Console.WriteLine(test_arr[i][j]);
            }
        }
    }
}


-- Result
A
B
C
D
E
F

가변 2차원 array를 for loop를 이용해서 참조한 예시입니다.

 

외부 array의 길이만큼 for loop를 돌리고,

내부 array의 길이만큼 내부 for loop를 한 번 더 돌려서 모든 요소를 참조하죠.

저희가 python같이 다른 프로그래밍 언어에서 흔히 사용하는 다차원 array가 바로 가변 array입니다.

(이후에 설명하겠지만 개수가 고정된 일반 다차원 array보다는 가변 array를 사용하는게 좀 더 편할겁니다.)

 

 

 

 

 

 

using System;

class MyProgram
{
    static void Main()
    {
        string[][] test_arr = new string[][]
        {
            new string[] {"A", "B", "C"},
            new string[] {"D", "E"},
            new string[] {"F"}
        };

        foreach (string[] i in test_arr)
        {
            foreach (string j in i)
            {
                Console.WriteLine(j);
            }
        }
    }
}


-- Result
A
B
C
D
E
F

가변 array를 foreach loop로 참조한 예시입니다.

 

 

 

 

 

 

using System;

class MyProgram
{
    static void Main()
    {
        string[,] test_arr = new string[4, 3]
        {
            {"과일", "Apple", "사과"},
            {"과일", "Peach", "복숭아"},
            {"야채", "Potato", "감자"},
            {"야채", "Carrot", "당근"}
        };

        for (int i = 0; i < test_arr.GetLength(0); i++)
        {
            for (int j = 0; j < test_arr.GetLength(1); j++)
            {
                Console.WriteLine(test_arr[i, j]);
            }
        };
    }
}


-- Result
과일
Apple
사과
과일
Peach
복숭아
야채
Potato
감자
야채
Carrot
당근

일반 2차원 array를 for loop에 적용한 예시입니다.

여기서 주의할점은 일반 2차원 array는 test_arr.GetLength(0), test_arr.GetLength(1) 같은 구문을 사용한 것을 주의해야합니다.

일반 2차원 array는 가변 array와는 달리 array 속에 array가 있다고 인식하기보다 2차원 array를 그냥 하나의 array 덩어리로 인식합니다.

따라서 array 속 내부 array의 Length를 인식할 수 없습니다.

 

이는 아래 예시를 보면 이해가 좀 더 될겁니다.

using System;

class MyProgram
{
    static void Main()
    {
        string[,] test_arr = new string[4, 3]
        {
            {"과일", "Apple", "사과"},
            {"과일", "Peach", "복숭아"},
            {"야채", "Potato", "감자"},
            {"야채", "Carrot", "당근"}
        };

        Console.WriteLine(test_arr.Length);
        Console.WriteLine(test_arr.GetLength(0));
        Console.WriteLine(test_arr.GetLength(1));
    }
}


-- Result
12
4
3

Console.WriteLine(test_arr.Length);

test_arr라는 2차원 array를 하나의 덩어리로 인식하기 때문에 Length가 12로 출력됩니다. 모든 요소의 개수이죠.

 

Console.WriteLine(test_arr.GetLength(0));

test_arr에 있는 0단계 array (가장 외부 array)가 가진 요소의 개수입니다.

이는 가장 외부 array 안에 있는 내부 array가 몇개 있는지를 의미합니다.

총 4개가 있으므로 4가 출력됩니다.

 

Console.WriteLine(test_arr.GetLength(1));

test_arr에 있는 1단계 array (내부 array)가 가진 요소의 개수입니다.

각각의 내부 array는 4개의 요소를 가지고 있으므로 3이 출력됩니다.

 

 

 

using System;

class MyProgram
{
    static void Main()
    {
        string[,] test_arr = new string[4, 3]
        {
            {"과일", "Apple", "사과"},
            {"과일", "Peach", "복숭아"},
            {"야채", "Potato", "감자"},
            {"야채", "Carrot", "당근"}
        };

        foreach (string i in test_arr)
        {
            Console.WriteLine(i);
        }
    }
}


-- Result
과일
Apple
사과
과일
Peach
복숭아
야채
Potato
감자
야채
Carrot
당근

일반 다차원 array는 그 array를 한 덩어리로 인식하기 때문에 foreach 구문을 한번만 사용하면 모든 요소를 다 return해줍니다.

 

 

 

여기까지 보면 일반 다른 언어를 학습하신 분들에게는 사실 일반 array보단 가변 array가 좀 더 익숙할겁니다.

for loop를 돌릴때에도 array 속의 array를 별도로 인식해서 외부 array와 내부 array의 indexing을 하는 등의 직관성이 좀 더 있는 것 같아보이네요.

 

 

 

 

 

 

728x90
반응형

'C# > C#' 카테고리의 다른 글

C# : static (정적 데이터)  (0) 2022.03.29
C# : abstract, virtual (class template 생성하기)  (0) 2022.03.23
C# : break, continue  (0) 2022.03.23
C# : while loop (반복문)  (0) 2022.03.23
C# : for loop, foreach loop (반복문)  (0) 2022.03.23
Comments