[C#] 09. 클래스 생성하는 방법(생성자, 소멸자)


Study/C#  2020. 7. 2. 17:47

안녕하세요. 명월입니다.

 

이 글은 C#에서 클래스 생성하는 방법(생성자, 소멸자)에 대한 글입니다.

 

C#에서 클래스는 프로그램을 실행을 위한 가장 최소 단위의 요소입니다. 즉, 프로그램을 실행하기 위해서 반드시 만들어져야 하는 요소라는 뜻입니다.

지금까지 우리는 Main 함수를 통해서 실행 함수를 만들었습니다.

그러나 그 Main 함수의 구조를 보면 함수를 감싸고 있는 Program의 클래스가 있고 클래스를 감싸는 Example이라는 네임스페이스가 있었습니다. (참고로 Namespace는 생략해도 프로그램을 작성하고 실행하는데 문제 없습니다.)

using System;

// Program 클래스
class Program
{
  // 실행 함수
  static void Main(string[] args)
  {
    // 콘솔 출력
    Console.WriteLine("Hello world");
    // 아무 키나 누르시면 종료합니다.
    Console.WriteLine("Press any key...");
    Console.ReadLine();
  }
}

위 예제를 보면 Namespace는 제거했고 Program의 클래스로 안에 Main 함수를 만들어서 최소 실행 단위를 만들었습니다. 에러없이 잘 실행됩니다.

 

그럼 이제 클래스의 구조에 대해서 설명하겠습니다.

public class 클래스명
{
  // 변수
  private int 변수 = 0;
  private int[] 변수2;
  
  // 델리게이트
  public delegate void 델리게이트();
  // 이벤트
  public event 이벤트델리게이트 이벤트;

  // 생성자
  public 클래스명()
  {
  }
  // 생성자
  public 클래스명(int i)
  {
  }
  // 소멸자
  ~클래스명()
  {
  }
  // 함수
  public void 메서드명()
  {

  }
  // 프로퍼티
  public int 프로퍼티
  {
    get;
    set;
  }
  //
  public int this[int i]
  {
    get { return 변수2[i]; }
    set { 변수2[i] = value; }
  }
}
클래스 맴버 설명
생성자 인스턴스가 생성(클래스가 메모리에 할당)될 때 호출되는 함수, 반환 타입은 없고 생성자명은 클래스 이름과 같다.
소멸자 인스턴스가 소멸(클래스가 메모리에 해제)될 때 호출되는 함수, 반환 타입은 없고 소멸자명은 클래스 이름 앞에 ~를 붙인 것과 같다.
맴버 변수 필드라고도 하는 멤버 변수는 클래스 내에서 사용하는 변수
프로퍼티 실행되는 동작은 함수와 비슷하나 사용하는 형태는 맴버 변수와 비슷한 요소
인덱서 실행되는 동작은 함수와 비슷하나 사용하는 형태는 맴버 배열과 비슷한 요소
함수 여러가지 실행 동작을 하는 요소
이벤트 특정적으로 중첩된 실행 단위(Queue)를 실행하는 함수

클래스의 기본 구조는 위와 같습니다. 여기서 위의 구조의 설명은 각 포스트로 나누어서 자세히 설명하겠습니다.


프로그램의 연산 처리하는 것을 CPU에서 처리하고 그 결과 값을 변수에 저장합니다만, 그 변수에 저장하는 것을 메모리에 보관하는 것과 같습니다.

클래스는 많은 요소가 있지만, 특히 맴버 변수라는 클래스 내부에서 사용하는 변수들이 있습니다. 로컬에서 사용하는 변수는 스택 영역이 종료 됨과 동시에 해제가 되지만, 프로그램에서 특정 변수 집합(클래스)를 메모리에 할당(공간 확보)하고 프로그램이 종료할 때까지 사용할 필요가 있습니다.

그것을 프로그램에서는 인스턴스 생성이라고 합니다.

클래스에서 맴버 변수가 int 타입이 두개 있다고 하면, 인스턴스 생성을 하게 되면 메모리에 4byte(int)의 인스턴스가 생성이 되는 것입니다.


먼저 인스턴스를 생성하는 방법은 new 키워드를 이용해서 생성합니다.

using System;

namespace Example
{
  // Exam 클래스
  class Exam
  {
    // 함수
    public void Print()
    {
      // 콘솔 출력
      Console.WriteLine("Hello world");
    }
  }
  class Program
  {
    static void Main(string[] args)
    {
      // 인스턴스 생성(클래스 호출)
      Exam exam = new Exam();
      // Exam의 Print 함수 호출
      exam.Print();
      // 아무 키나 누르시면 종료합니다.
      Console.WriteLine("Press any key...");
      Console.ReadLine();
    }
  }   
}

위 소스에서 Main함수에서 Exam의 클래스를 인스턴스 생성을 해서 Print() 함수를 실행했습니다.

 

클래스의 요소 중에는 생성자가 있습니다. 이 생성자는 클래스의 인스턴스가 생성될 때 호출되는 함수라고 생각하면 됩니다.

생성자는 함수의 특징인 다형성이 가능하여 파라미터 별로 호출이 가능합니다.

using System;

namespace Example
{
  // Exam 클래스
  class Exam
  {
    // 생성자
    public Exam()
    {
      // 콘솔 출력
      Console.WriteLine("call constructor - no parameter");
    }
    // 생성자
    public Exam(int a)
    {
      // 콘솔 출력
      Console.WriteLine("call constructor - parameter " + a);
    }
  }
  class Program
  {
    static void Main(string[] args)
    {
      // 인스턴스 생성(클래스 호출)
      // 파라미터가 없는 생성자 호출
      Exam exam = new Exam();
      // 인스턴스 생성(클래스 호출)
      // int형 파라미터 생성자를 호출
      Exam exam1 = new Exam(0);
      // 아무 키나 누르시면 종료합니다.
      Console.WriteLine("Press any key...");
      Console.ReadLine();
    }
  }
}

인스턴스를 생성할 때(new 클래스명())에서 파라미터에 의해 호출되는 생성자가 다릅니다. 호출하는 방법도 함수와 비슷하네요.


그리고 클래스에서 소멸자가 있습니다. 이 소멸자는 앞에 생성자와 비슷하게 클래스명과 같은 이름의 소멸자명에 앞에 물결(~) 표시가 설정됩니다.

이 소멸자는 인스턴스가 사라질 때 발생하는 함수입니다. 근데 실제 C#에서는 이 소멸자를 사용할 일이 없습니다.

C/C++에서는 메모리 해제를 프로그램 소스 안에서 설정하지만 C#은 가비지 컬렉션(GC)에서 메모리를 해제하기 때문에, 이 소멸자가 언제 발생하는 지는 알 수가 없습니다.(유저가 메모리 해제를 설정할 수도 없습니다.)

그렇기 때문에 이 언제 호출될 지도 모르기 떄문에, 이 소멸자를 사용할 일은 없다고 생각합니다.

C#의 언어는 C/C++에서 파생된 언어이기 때문에 필요없는 잔재가 남아 있네요.

 

여기까지 C#에서 클래스 생성하는 방법(생성자, 소멸자)에 대한 글이었습니다.

 

궁금한 점이나 잘못된 점이 있으면 댓글 부탁드립니다.