Menu
Coddy logo textTech

Final 및 Const 필드

Coddy Dart 여정의 객체 지향 프로그래밍 섹션에 포함된 레슨 — 110개 중 18번째.

클래스에서 필드를 선언할 때, final 또는 const를 사용하여 초기화 후 값이 변경될 수 있는지 여부를 제어할 수 있습니다. 둘 다 불변 값을 생성하지만, 작동 방식은 다릅니다.

final 필드는 한 번만 설정할 수 있지만, 그 값은 런타임에 결정됩니다. 선언 시 또는 생성자를 통해 할당할 수 있습니다:

class Person {
  final String name;
  final DateTime createdAt = DateTime.now();
  
  Person(this.name);
}

Person p = Person('Alice');
// p.name = 'Bob';  // 오류: final 필드는 재할당할 수 없습니다

객체가 생성될 때 name이 설정되며, createdAt은 현재 시간을 캡처합니다. 두 값 모두 초기화 후에는 고정됩니다.

static const 필드는 컴파일 타임에 알 수 있는 값을 가져야 합니다. 이는 클래스 자체에 속하며 모든 인스턴스에서 공유됩니다:

class Circle {
  static const double pi = 3.14159;
  final double radius;
  
  Circle(this.radius);
  
  double get area => Circle.pi * radius * radius;
}

주요 차이점: final 필드는 런타임에 계산된 값(예: DateTime.now())을 가질 수 있는 반면, const는 컴파일 타임 상수를 필요로 합니다. 인스턴스 필드는 직접 const가 될 수 없으며, 클래스 수준에서는 static const만 허용됩니다.

challenge icon

챌린지

쉬움

finalstatic const 필드의 차이점을 보여주는 제품 카탈로그 시스템을 구축해 보겠습니다. 불변 속성과 공유 설정 값을 가진 제품을 만들게 됩니다.

코드를 두 개의 파일로 구성합니다:

  • product.dart: 상점의 품목을 나타내는 Product 클래스를 정의합니다. 클래스에는 다음이 포함되어야 합니다:
    • 0.08로 설정된 static const double taxRate (모든 제품에 공유되는 8% 세율)
    • 'USD'로 설정된 static const String currency
    • 제품 이름을 위한 final String name (생성자를 통해 설정)
    • 제품의 기본 가격을 위한 final double basePrice (생성자를 통해 설정)
    • 접두사와 제품 이름을 결합한 final String sku (재고 관리 단위). 초기화 리스트에서 'SKU-' 뒤에 대문자로 변환된 이름을 붙여 계산됩니다.
    • namebasePrice를 인자로 받는 생성자
    • 세금을 포함한 가격을 계산하는 게터(getter) priceWithTax
    • 제품 정보를 출력하는 display() 메서드
  • main.dart: 제품 클래스를 임포트하고 두 개의 제품을 생성합니다:
    • 기본 가격이 999.99'Laptop'
    • 기본 가격이 29.99'Mouse'
    위에 나열된 순서대로 각 제품에 대해 display()를 호출합니다.

display() 메서드는 반드시 다음 형식으로 출력해야 합니다:

[sku] - [name]: [basePrice] [currency] (with tax: [priceWithTax] [currency])

출력 시 toStringAsFixed(2)를 사용하여 priceWithTax를 소수점 둘째 자리까지 반올림하세요.

예상 출력:

SKU-LAPTOP - Laptop: 999.99 USD (with tax: 1079.99 USD)
SKU-MOUSE - Mouse: 29.99 USD (with tax: 32.39 USD)

치트 시트

런타임에 한 번 설정되고 이후에 변경할 수 없는 필드에는 final을 사용하세요. 클래스의 모든 인스턴스에서 공유되는 컴파일 타임 상수의 경우에는 static const를 사용하세요.

final 필드는 런타임에 설정되며 선언부 또는 생성자에서 초기화할 수 있습니다:

class Person {
  final String name;
  final DateTime createdAt = DateTime.now();
  
  Person(this.name);
}

static const 필드는 반드시 컴파일 타임 상수 값을 가져야 하며 클래스 자체에 속합니다:

class Circle {
  static const double pi = 3.14159;
  final double radius;
  
  Circle(this.radius);
  
  double get area => Circle.pi * radius * radius;
}

초기화 리스트(initializer list)에서 final 필드 값을 계산할 수 있습니다:

class Product {
  final String name;
  final String sku;
  
  Product(this.name) : sku = 'SKU-${name.toUpperCase()}';
}

주요 차이점:

  • final: 런타임 값, 각 인스턴스마다 다를 수 있음
  • static const: 컴파일 타임 상수, 모든 인스턴스에서 공유됨
  • 인스턴스 필드는 직접 const가 될 수 없으며, static const만 허용됩니다.

직접 해보기

import 'product.dart';

void main() {
  // TODO: 기본 가격이 999.99인 'Laptop'이라는 Product를 생성하세요
  
  // TODO: 기본 가격이 29.99인 'Mouse'라는 Product를 생성하세요
  
  // TODO: 각 제품에 대해 순서대로 (Laptop 먼저, 그다음 Mouse) display()를 호출하세요
  
}
quiz icon실력 점검

이 레슨에는 짧은 퀴즈가 포함되어 있습니다. 레슨을 시작해 문제를 풀고 진행 상황을 기록하세요.

객체 지향 프로그래밍의 모든 레슨