본문 바로가기
다트(Dart) 언어 강좌

객체 지향 프로그래밍의 핵심을 알아보자

by everythingdev 2024. 7. 24.
반응형

객체 지향 프로그래밍의 핵심을 알아보자

  • 플러터를 시작하기 전 다트(Dart) 언어의 개념에 대해 정리를 해보고자 합니다.
  • 다트(Dart) 언어 개념 정리 포스팅 후 플러터(Flutter) 개념 정리로 넘어갈 예정입니다.
  • 플러터(Flutter) 개념 정리 후 실습이 시작 된다고 보시면 될 것 같습니다.

소개

  • Dart는 구글이 개발한 현대적이고 강력한 프로그래밍 언어입니다.
  • 특히 Flutter 프레임워크와 함께 사용되어 크로스 플랫폼 앱 개발에 널리 활용되고 있습니다.
  • Dart의 핵심 기능 중 하나는 객체 지향 프로그래밍(OOP)을 완벽하게 지원한다는 점입니다.
  • 이번 포스팅에서는 Dart의 클래스와 객체에 대해 자세히 알아보겠습니다.

클래스의 기본 개념

클래스는 객체 지향 프로그래밍의 기본 단위입니다. 클래스는 관련된 데이터와 기능을 하나의 단위로 묶어 표현합니다. Dart에서 클래스를 정의하는 방법은 다음과 같습니다:

class Person {
  String name;
  int age;

  void introduce() {
    print('안녕하세요, 제 이름은 $name이고 나이는 $age살입니다.');
  }
}

  • 이 예제에서 Person 클래스는 nameage라는 두 개의 속성(필드)과 introduce()라는 메서드를 가지고 있습니다.

객체 생성하기

클래스를 정의한 후에는 해당 클래스의 인스턴스, 즉 객체를 생성할 수 있습니다. Dart에서 객체를 생성하는 방법은 다음과 같습니다:

void main() {
  var person = Person();
  person.name = '홍길동';
  person.age = 30;
  person.introduce();
}
  • 이 코드는 Person 클래스의 새로운 인스턴스를 생성하고, 속성 값을 설정한 후 introduce() 메서드를 호출합니다.

생성자

생성자는 객체를 초기화하는 특별한 메서드입니다. Dart에서는 여러 종류의 생성자를 정의할 수 있습니다:

기본 생성자

class Person {
  String name;
  int age;

  Person(this.name, this.age);
}

명명된 생성자

class Person {
  String name;
  int age;

  Person(this.name, this.age);

  Person.guest() {
    name = '손님';
    age = 0;
  }
}

팩토리 생성자

class Circle {
  double radius;

  Circle(this.radius);

  factory Circle.fromDiameter(double diameter) {
    return Circle(diameter / 2);
  }
}

상속

Dart에서는 extends 키워드를 사용하여 클래스 상속을 구현할 수 있습니다:

class Student extends Person {
  String school;

  Student(String name, int age, this.school) : super(name, age);

  @override
  void introduce() {
    super.introduce();
    print('저는 $school에 다니고 있습니다.');
  }
}
  • 이 예제에서 Student 클래스는 Person 클래스를 상속받아 추가적인 school 속성과 오버라이드된 introduce() 메서드를 가지고 있습니다.

추상 클래스와 인터페이스

Dart에서는 abstract 키워드를 사용하여 추상 클래스를 정의할 수 있습니다:

abstract class Shape {
  double getArea();
}

class Rectangle extends Shape {
  double width;
  double height;

  Rectangle(this.width, this.height);

  @override
  double getArea() {
    return width * height;
  }
}

Dart에서는 별도의 interface 키워드가 없습니다. 대신 모든 클래스가 암시적으로 인터페이스 역할을 할 수 있습니다:

class Flyable {
  void fly() {
    print('날고 있습니다!');
  }
}

class Bird implements Flyable {
  @override
  void fly() {
    print('새가 날고 있습니다!');
  }
}

믹스인

Dart는 with 키워드를 사용하여 믹스인을 지원합니다. 믹스인은 클래스 간에 코드를 재사용할 수 있는 강력한 방법입니다:

mixin Logger {
  void log(String message) {
    print('로그: $message');
  }
}

class Database with Logger {
  void save() {
    log('데이터를 저장했습니다.');
  }
}

게터와 세터

Dart에서는 getset 키워드를 사용하여 게터와 세터를 정의할 수 있습니다:

class Temperature {
  double _celsius;

  Temperature(this._celsius);

  double get fahrenheit => _celsius * 9 / 5 + 32;

  set fahrenheit(double value) {
    _celsius = (value - 32) * 5 / 9;
  }
}
  • 이 예제에서 fahrenheit 게터와 세터를 통해 섭씨 온도를 화씨 온도로 변환하거나 그 반대로 변환할 수 있습니다.

정적 멤버

클래스의 인스턴스가 아닌 클래스 자체에 속하는 멤버를 정의하려면 static 키워드를 사용합니다:

class MathUtils {
  static const double PI = 3.14159;

  static double circleArea(double radius) {
    return PI * radius * radius;
  }
}
  • 이 예제에서 PIcircleArea() 메서드는 MathUtils 클래스의 정적 멤버입니다.

결론

  • Dart의 클래스와 객체는 강력하고 유연한 객체 지향 프로그래밍을 가능하게 합니다. 이 글에서 다룬 개념들은 Dart로 효과적인 프로그램을 작성하는 데 필수적입니다. 클래스와 객체를 잘 활용하면 코드의 재사용성과 유지보수성을 크게 향상시킬 수 있습니다.
  • Dart의 객체 지향 기능을 완전히 익히려면 실제 프로젝트에서 이러한 개념들을 적용해보는 것이 중요합니다. Flutter와 같은 프레임워크를 사용하여 앱을 개발하면서 이러한 개념들을 실제로 적용해볼 수 있습니다.
  • 또한, Dart의 공식 문서와 커뮤니티 리소스를 활용하여 더 깊이 있는 지식을 쌓는 것도 좋습니다. 객체 지향 프로그래밍의 원칙과 패턴을 학습하고 Dart에서 어떻게 구현되는지 이해하면, 더욱 효과적이고 유지보수가 용이한 코드를 작성할 수 있을 것입니다.

맺음말

  • 이번 포스팅에서는 다트의 클래스와 객체에 대해 알아보았습니다.
  • 다음 포스팅에서는 다트의 생성자와 메서드에 대해 알아보고자 합니다.
반응형