[C#] 자료 구조 – Stack

[C#] 자료 구조 – Stack

개요

이번 글에서는 C#에서 사용되는 스택, Stack<T>에 대해 알아보겠습니다. Stack<T> 또한 C#의 제네릭 컬렉션 클래스로 LIFO(Last In, First Out) 방식으로 데이터를 관리하는 자료 구조 입니다. 다른 자료 구조와 마찬가지로 T에는 다양한 타임의 데이터를 지정할 수 있습니다.

생성

Stack<T> 컬렉션 클래스를 선언하는 방법은 아래와 같습니다.

Stack<T> list = new Stack<T>();

다른 자료구조와 클래스와 마찬가지로 T에는 어떠한 자료형이든 올 수 있습니다.

함수 및 속성

함수와 속성에 대해서 먼저 설명하겠습니다. 자주 사용하는 함수 및 속성은 아래와 같습니다.

속성 및 함수설명
Count스택에 있는 요소의 개수를 반환합니다.
Push(T item)스택의 맨 위에 새 요소를 추가합니다.
Pop()스택의 맨 위에 있는 요소를 제거하고 반환합니다.
Peek()스택의 맨 위에 있는 요소를 제거하지 않고 반환합니다.
Clear()스택의 모든 요소를 제거합니다.
Contains(T item)특정 요소가 스택에 있는지 확인합니다.
ToArray()스택의 요소를 배열로 복사하여 반환합니다.

예제 – 웹 브라우저 주소 이동

만들어 볼 예제는 웹 브라우저의 주소 이동을 하는 프로그램입니다. 실제 브라우저는 아니고, 브라우저의 주소 입력, 이전 페이지, 다음 페이지 기능을 스택으로 구현하려 합니다.

웹 브라우저의 경우 주소창에 주소를 입력하면 해당 주소로 이동합니다. 하지만 이동을 몇 번 하 보면 이전 페이지로 이동이 가능하며 다음 페이지로도 이동이 가능합니다.

주소를 저장하는 CWebAddress 클래스와 웹 브라우저를 의미하는 CWebBrowser 클래스를 아래와 같이 만들어줍니다.

// 웹브라우저public class CWebBrowser
{
    private Stack<CWebAddress> _stackPrev = new Stack<CWebAddress>(); // 이전 페이지 관리 스택
    private Stack<CWebAddress> _stackNext = new Stack<CWebAddress>(); // 다음 페이지 관리 스택

    public CWebBrowser()
    {
    }

    public void DoRun()
    {
        // todo .. : 
    }
}

// 웹 주소
public class CWebAddress
{
    private string _address;

    public CWebAddress(string address)
    {
        _address = address;
    }

    public override string ToString()
    {
        return $"현재 주소: {_address}";
    }
}

그리고 CWebBrowser 클래스 DoRun 함수에 아래와 같이 코딩합니다.

public void DoRun()
{
    _stackPrev.Clear();
    _stackNext.Clear();
    _stackPrev.Push(new CWebAddress("https://3001ssw.com")); // 기본 페이지 입력

    Console.WriteLine("브라우저를 시작합니다.");

    while (true)
    {
        Console.WriteLine("==============================================================");
        Console.WriteLine($"현재 페이지: {_stackPrev.Peek()}");
        Console.WriteLine("(새 주소 입력 - 문자열, 이전페이지 - p, 다음페이지 - n, 종료 - X)");
        string? strRead = Console.ReadLine();

        if (string.IsNullOrWhiteSpace(strRead) == false)
        {
            strRead = strRead.ToUpper();

            // 이전 페이지 이동
            if (strRead.Equals("P"))
            {
                if (_stackPrev.Count <= 1)
                    Console.WriteLine("이전 페이지가 없습니다.");
                else
                    _stackNext.Push(_stackPrev.Pop()); // 이전페이지 스택에서 Pop, 다음페이지 스택에 Push
            }
            // 다음 페이지
            else if (strRead.Equals("N"))
            {
                if (_stackPrev.Count == 0 || _stackNext.Count == 0)
                    Console.WriteLine("다음 페이지가 없습니다.");
                else
                    _stackPrev.Push(_stackNext.Pop()); // 다음페이지 스택에서 Pop, 이전페이지 스택에 Push
            }
            // 종료
            else if (strRead.Equals("X"))
                break;
            // 주소 입력
            else
            {
                strRead = strRead.ToLower();

                _stackPrev.Push(new CWebAddress(strRead)); // 주소 입력
                _stackNext.Clear();
            }
        }
    }
    _stackPrev.Clear();
    _stackNext.Clear();
    Console.WriteLine("브라우저를 종료합니다.");
}

실행하면 아래와 같이 볼 수 있습니다.

처음 시작은 제 블로그(3001ssw.com) 주소가 기본값으로 입력 되어 있고, 제가 네이버(www.naver.com), 그 다음으로 구글(ww.google.com) 주소를 입력하였습니다. 보시는 것과 같이 주소 입력할 때마다 입력한 현재 페이지를 계속 표시하고 있으며, 이전으로 돌아가는 명령어를 입력하면 다시 네이버, 블로그 주소로 이동하며, 다음 페이지로 이동하는 것 또한 잘 됩니다.

전체 코드는 아래 깃헙 링크 참고하시기 바랍니다.


github : https://github.com/3001ssw/c_sharp/tree/main/Data_Struct/Stack