Dart는 강력한 정적 타입 언어로, 모든 변수는 특정 데이터 타입을 가진다. Dart의 데이터 타입은 크게 기본 타입과 컬렉션 타입으로 나눌 수 있으며, 사용자가 정의한 타입을 포함한 다양한 확장성도 제공한다.
숫자형 (Numbers)
Dart에서는 int
와 double
두 가지 주요 숫자형 타입이 존재한다.
정수형 (int)
정수형은 부호가 있는 64비트의 정수로 표현되며, int
타입으로 선언한다. 다음은 정수형의 특징이다.
- 표현 가능한 값의 범위: -2^{63} 에서 2^{63}-1 까지
- 부호가 있는 64비트 정수
- 예시:
int x = 5;
실수형 (double)
실수형은 IEEE 754 표준에 따른 64비트 부동소수점으로 표현되며, double
타입으로 선언된다. 실수형은 매우 큰 값 또는 매우 작은 값을 표현할 때 사용한다.
- 실수형 예시:
double y = 3.14;
수학적 표현
변수 x 가 정수형이라면:
변수 y 가 실수형이라면:
이렇게 정수형과 실수형을 사용하여 다양한 계산이 가능하다.
문자열 (Strings)
문자열은 String
타입으로 선언되며, 유니코드 텍스트를 포함할 수 있다. Dart에서 문자열은 큰따옴표(" "
) 또는 작은따옴표(' '
)로 감싸서 표현할 수 있다.
문자열 선언 예시:
String name = 'ChatGPT';
여러 줄 문자열
여러 줄 문자열은 세 개의 작은따옴표(''' '''
) 또는 큰따옴표(""" """
)로 감싸서 작성할 수 있다.
String multiline = '''
이 문자열은
여러 줄로 작성되었다.
''';
문자열 보간법
Dart에서는 문자열 내에서 변수를 쉽게 삽입할 수 있는 문자열 보간법을 제공한다. 문자열 보간은 $
기호를 사용하여 변수를 삽입하거나 표현식을 중괄호({}
)로 감싸서 사용한다.
String greeting = 'Hello, $name!';
또는 표현식을 포함할 수 있다:
String message = '2 + 2 equals ${2 + 2}';
불리언 (Booleans)
불리언 타입은 bool
로 선언되며, 두 가지 값만 가질 수 있다: true
또는 false
. 불리언 값은 주로 조건문에서 사용된다.
예시:
bool isVisible = true;
컬렉션 타입 (Collections)
Dart는 List
, Set
, Map
등의 기본 컬렉션 타입을 제공한다. 각 컬렉션은 데이터를 저장하고 관리하는 데 사용되며, 각각의 특징이 다르다.
List
List
는 순서가 있는 데이터의 집합이며, 배열처럼 사용할 수 있다. Dart의 List
는 가변 길이를 지원하며, 고정 길이로도 선언할 수 있다.
List<int> numbers = [1, 2, 3, 4];
Set
Set
은 순서가 없는 고유한 값들의 집합이다. Set
은 중복된 요소를 허용하지 않는다.
Set<String> uniqueNames = {'Alice', 'Bob', 'Charlie'};
Map
Map
은 키와 값의 쌍으로 이루어진 컬렉션이다. 각 키는 고유하며, 이를 통해 값에 접근할 수 있다.
Map<String, int> ages = {
'Alice': 25,
'Bob': 30,
};
Null 허용 및 Null 안전성 (Null Safety)
Dart에서는 Null Safety 기능을 통해 변수나 객체가 null
값을 가질 가능성을 명시적으로 제어할 수 있다. 기본적으로 Dart에서는 모든 변수는 null을 허용하지 않으며, 반드시 초기화되어야 한다. 만약 변수에 null 값을 허용하려면 타입 선언 시 ?
를 추가해야 한다.
Null 허용 변수 선언 예시:
int? age = null;
위 코드에서 age
변수는 null
값을 가질 수 있는 정수형으로 선언되었다. 이를 통해 null 값에 안전하게 접근할 수 있다.
Null 값 접근 시 안전 연산자
변수에 null 값을 안전하게 접근하려면 Dart에서 제공하는 안전 연산자를 사용할 수 있다.
- null-aware 연산자 (
?.
): 변수가 null일 때 호출을 막아준다. - 널 병합 연산자 (
??
): null일 경우 대체 값을 제공한다.
예시:
String? name;
print(name?.toUpperCase() ?? 'Unknown');
위 코드는 name
이 null일 경우 'Unknown'을 출력하며, 그렇지 않으면 name
의 값을 대문자로 변환해 출력한다.
동적 타입 (dynamic)
Dart에서는 dynamic
타입을 사용하여 특정 타입에 구애받지 않고 다양한 데이터 타입을 가질 수 있는 변수를 선언할 수 있다. 하지만 동적 타입의 사용은 타입 안전성을 감소시킬 수 있으므로 필요한 경우에만 사용하는 것이 권장된다.
동적 타입 예시:
dynamic variable = 'Hello';
variable = 42; // 가능
dynamic
타입은 컴파일 시 타입 검사를 생략하고, 런타임에 타입을 결정한다.
타입 추론
Dart에서는 타입 추론(Type Inference) 기능을 제공하여, 변수를 선언할 때 명시적으로 타입을 지정하지 않아도 Dart가 자동으로 타입을 추론할 수 있다. 이를 통해 코드가 더욱 간결해진다. Dart에서는 var
키워드를 사용하여 타입을 명시하지 않고 변수를 선언할 수 있다.
타입 추론 예시:
var number = 10; // int로 추론됨
var message = 'Hello'; // String으로 추론됨
주의할 점:
var
키워드로 선언된 변수는 최초 할당된 값에 따라 타입이 고정된다. 따라서 같은 변수에 다른 타입의 값을 할당할 수 없다.
var text = 'Hello';
// text = 42; // 컴파일 에러 발생
타입 캐스팅
Dart에서는 타입 캐스팅을 통해 특정 타입의 객체를 다른 타입으로 변환할 수 있다. as
키워드를 사용하여 명시적인 캐스팅을 수행할 수 있다.
타입 캐스팅 예시:
dynamic value = 'Hello';
String message = value as String;
캐스팅이 성공하면 변환된 값을 사용할 수 있으며, 캐스팅에 실패하면 런타임 오류가 발생할 수 있다. 이를 방지하기 위해 is
키워드를 사용하여 타입을 미리 확인할 수 있다.
타입 확인 예시:
if (value is String) {
print('value는 문자열이다.');
}
is
키워드를 사용하면 객체가 특정 타입인지 확인한 후 안전하게 캐스팅할 수 있다.