본문 바로가기
개발언어/C#

[C#] Nullable type, int? 널러블 타입

by 창용이랑 2023. 5. 22.
728x90

오늘은 C#에 존재하는 특별한 타입인 Nullable Type에 대해서 이야기 해보려합니다.

다들 C# 코드를 보다보면 "int 물음표"(=int?) 타입을 가끔씩 보시지 않았나요?

아니, int 타입이면 int 만 쓸것이지 뒤에 물음표는 뭐지? 하시는 분들이 있을 것 입니다.

C#에서는 Null을 가질 수 없는 타입들에게 특별히 Null을 가질 수 있게 하는 Nullable Type 이라는 개념을 도입했습니다.

(java에서도 비슷한게 있다는걸 들었는데.. java는 공부를 안해서..모르겠네요)

목차

1. Nullable Type 이란?

2. Nullable Type의 선언 방법, 속성과 메서드, 사용법 및 주의점

3. 다양한 Nullable Type 예제

4. Nullable 다시한번 총정리

그럼 이제 시작해보겠습니다.

 

1. Nullable Type 이란?


 

- C# Nullable Type 이란 Null 을 가질 수 없는 데이터 타입을 Null을 가질 수 있는 타입으로 만든 새로운 타입입니다.

 

- 대표적으로 값 타입(value type)들이 Null을 가질 수 없는데요. int, 구조체, double, bool 등의 데이터 타입은 값이 없는 상태(NULL)이 불가능한 데이터 타입들 입니다.

(클래스와 같은 reference type(=참조 타입)은 이미 Null 체크가 가능하기 때문에 따로 Nullable Type으로 만들지 않아도 됩니다.)

 

- int와 같은 값 타입에 대해서 "값이 없다"를 표현하기 위해 Nullable Type이 개발 되었다 라고 생각하시면 좋을듯 합니다.

 

- 우리는 int를 nullable int type으로 변경함으로서 값이 할당 되었는지 아닌지(null) 확인 할 수 있게 되었습니다.

 

 

2. Nullable Type의 선언 방법, 속성과 메서드, 사용법, 주의점


 

 선언 방법

아래 두가지 방법으로 선언이 가능합니다. 

개인적으로는 "데이터 타입 + ?" 방법이 더 보기 편하다고 생각이 듭니다.

 

Nullable<T> 변수명

T? 변수명

 

- 선언 예시 

Nullable<int> num;

int? num;

 

▶ 속성과 메서드

1. HasValue 속성

값이 있는 경우  : true

값이 없는 경우(Null) : false

 

2. Value 속성

값이 있는 경우 : 할당된 값

값이 없는 경우(null) : 예외(Exception) 발생 

 

3. GetValueOrDefault() 메서드

값이 있는 경우 : 할당된 값 반환

값이 없는 경우(Null) : 기존 타입의 default 값 반환

 

▶ 사용법

Nullable<int> a;    // int? a;

a = null;

Console.WriteLine(a);                         // null이 나옵니다.

Console.WriteLine(a.HasValue);        // 할당된 값이 없으므로 false

Console.WriteLine(a.Value);                // 할당된 값이 없으므로 예외

Console.WriteLine(a.GetValueOrDefault()); // 할당된 값이 없으므로 int 타입의 default 값인 0 이 반환됩니다.

 

int? b;            // Nullable<int> b;

b = 10;

Console.WriteLine(b);                         // 10이 나옵니다.

Console.WriteLine(b.HasValue);        // 할당된 값이 있으므로 true

Console.WriteLine(b.Value);                // 할당된 값이 있으므로 10

Console.WriteLine(b.GetValueOrDefault()); // 할당된 값이 있으므로 10이 반환됩니다.

 

▶ 주의점

- Nullable 중복 불가능

Nullable<Nullbale<int>> num; //불가능

 

- Value를 접근할때는 HasValue로 체크 한 후에 접근하기.

위에 예시에서 보셨겠지만 값이 존재하지 않는 Null인 경우 Value에 바로 접근하게 되면 예외가 발생하며 프로세스가 죽을 위험이 있습니다.

그렇기 때문에 HasValue로 값이 존재하는지 체크 한 후 에 Value에 안전하게 접근하는 방법을 추천드립니다.

 

- int, int?는 엄연히 다른 타입이므로 명시적 형 변환이 필요합니다.

 

3. Nullable Type 예제


 

▶int? 예제 1번 (메서드와 속성의 사용법)

static void Main(string[] args)
{
 
    Nullable<int> a;
    a = null;
 
    Console.WriteLine("Nullable<int> a : Null 일 때");
    Console.WriteLine("a : {0}", a);
    Console.WriteLine("a.HasValue : {0} ", a.HasValue);
    //Console.WriteLine("a.Value : {0} ", a.Value);    // 할당된 값이 없으므로 예외
    Console.WriteLine("a.GetValueOrDefault() : {0} ", a.GetValueOrDefault());
 
    Console.WriteLine();
 
    a = 10;
    Console.WriteLine("Nullable<int> a : 10 일 때");
    Console.WriteLine("a : {0}", a);
    Console.WriteLine("a.HasValue : {0} ", a.HasValue);
    Console.WriteLine("a.Value : {0} ", a.Value);
    Console.WriteLine("a.GetValueOrDefault() : {0} ", a.GetValueOrDefault());
}

▷1번 결과

 

▶Nullable Type 예제 2번(실제 프로그램을 만들때 사용하는 방법)

static void Main(string[] args)
{
 
    int? a = null;  // or 22;
 
    if (a.HasValue) //HasValue로 값체크 먼저 수행
    {
        //Null이 아닌 값이 들어있다.
        Console.WriteLine("a is not Null");
        Console.WriteLine($"a.Value : {a.Value}");  //그리고 값에 접근
    }
    else
    {
        //Null 이다.
        Console.WriteLine("a is Null");
    }
}

▷2번 결과

a 가 null 일때와 22일때 각각의 출력 결과를 보여 줍니다.

 

▶Nullable Type 예제 3번(배열에 적용하는 방법)

static void Main(string[] args)
{
    int?[] arr = new int?[10];
 
    arr[0] = 10;
    arr[2] = 12;
    arr[5] = 15;
    arr[7] = 17;
 
    foreach (var num in arr) //var 대신 int? 사용가능.
    {
        if (num.HasValue)
        {
            //배열에서 값이 할당된 것들만 출력.
            Console.WriteLine($"num = {num.Value}");
        }
    }
}

▷3번 결과

 

4. Nullable 총 정리


- nullable 형식은 값형식의 데이터 타입에 Null 값을 넣을수 있도록 해주는 형식입니다.

- HasValue 속성을 통해서 null이 아닌 값이 할당되었는지 확인할 수 있습니다.

- Value 속성을 통해서 할당된 값을 확인할수 있지만, 만약 할당 값이 없다면 예외 던집니다. 그렇기 때문에 HasValue를 통해서 값이 있는지 확인 후에 Value 속성을 확인하는걸 추천 드립니다.

- GetValueOrDefault() 메소드는 값이 있다면 해당 값을 반환하고, 만약 값이 없다면 해당 데이터 타입의 기본(Default)값을 반환합니다.

 

출처 : https://blockdmask.tistory.com/360