[Dart] #4 Class

ZenTechie·2023년 8월 21일
0

Dart

목록 보기
4/4
post-thumbnail

Class 만들고 사용하기

  • class에서 property를 선언할 때는 명시적 타입을 반드시 사용해서 정의해야 한다.
  • class 내의 함수에서 property를 사용할 때는 this를 사용하지 않는다.(Flutter에서 권고하는 사항)
class Info {
  String name = 'zenTechie';
  int age = 26;

  void hello() {
    print('Hello, $name');
  }
}

void main() {
  var person = Info();
  person.hello();
}

만약, 함수 내에 property의 이름과 동일한 변수가 있다면, this를 사용해야 한다.

class Info {
  String name = 'zenTechie';
  int age = 26;

  void hello() {
    var name = 'zenCoder';
    print('Hello, ${this.name}');
  }
}

void main() {
  var person = Info();
  person.hello();
}

그리고 instance를 만들때는 new 키워드를 붙이지 않는다!


생성자

생성자 함수의 이름은 class의 이름과 동일해야 한다.

late를 사용하는 방식

class Info {
  // late를 사용해야 한다.
  late String name;
  late int age;
  
  Info(String name, int age) {
    this.name = name;
    this.age = age;
  }
  void hello() {
    print('Hello, ${this.name}');
  }
}

void main() {
  var person = Info('zenTechie', 26);
  person.hello();
}

late를 사용하지 않는 방식

class Info {
  // late를 사용해야 한다.
  String name;
  int age;

  Info(this.name, this.age);
  
  void hello() {
    print('Hello, ${this.name}');
  }
}

void main() {
  var person = Info('zenTechie', 26);
  person.hello();
}

위 방식이 코드가 더 간결해진다!


Named Constructor Parameters

이전에 배운 Named Parameters를 생성자에도 적용할 수 있다.

class Info {
  // late를 사용해야 한다.
  String name;
  int age;

  Info({required this.name, required this.age});
}

void main() {
  var person = Info(
    name: 'zenTechie',
    age: 26,
  );
}

--

Named Constructors

서로 다른 생성자 함수를 만들고 싶을 때 사용하는 것이 Named COnstructors이다.

생성자이름.생성자함수이름() : property 초기화 코드1, property 초기화 코드2, property 초기화 코드3
class Info {
  // late를 사용해야 한다.
  String name;
  int age;
  String type;

  Info.createMyInfo({required String name, required int age})
      : this.name = name,
        this.age = age,
        this.type = 'Me';
  Info.createYourInfo({required String name, required int age})
      : this.name = name,
        this.age = age,
        this.type = 'You';
}

void main() {
  var me = Info.createMyInfo(
    name: 'zenTechie',
    age: 26,
  );
  var you = Info.createYourInfo(
    name: 'John',
    age: 30,
  );
}

: 뒤는 class의 property를 초기화 해주는 코드이다.

위 코드에서는 Named Constructors에서 type을 서로 다르게 지정했다.

class의 property를 초기화 할 때 this를 꼭 붙여야 하나?
➡️ 디폴트 생성자에서는 this를 써야하지만, 그렇지 않다면 굳이 쓰지 않아도 된다?


Cascade Notation

Info 객체를 하나 생성하고, property의 value를 바꾼다고 해보자. 기본적으로는 아래와 같이 바꿀 수 있다.

class Info {
  String name;
  int age;
  String type;

  Info({required this.name, required this.age, required this.type});

  void printInfo() {
    print('name: $name, age: $age, type: $type');
  }
}

void main() {
  var zen = Info(name: 'zen', age: 26, type: 'male');
  zen.name = 'zen2';
  zen.age = 30;
  zen.type = 'female';
}

Cascade Operator을 사용하여 바꿀 수 있다.

class Info {
  String name;
  int age;
  String type;

  Info({required this.name, required this.age, required this.type});

  void printInfo() {
    print('name: $name, age: $age, type: $type');
  }
}

void main() {
  var zen = Info(name: 'zen', age: 26, type: 'male')
  ..name = 'zen2'
  ..age = 30
  ..type = 'female'
  ..printInfo(); // == zen.printInfo()
}

방법은 다음과 같다.

  1. Info(생성자)뒤에 ;을 지운다.
  2. 인스턴스의 이름 대신 ..을 사용한다.
    ➡️ ..name은 기존 코드에서 zen.name을 의미한다.
  3. ;은 마지막 줄에만 붙인다.

생성자 초기화 직후가 아니어도 된다. 나중에도 할 수 있다.


Enum

가끔 코딩을 하다보면, flex를 felx, margin-bottom mrgin-bottom 으로 잘못 작성하는 경우가 있다.

Enum은 이러한 실수를 하지 않도록 도와주는 타입이라고 볼 수 있다. (Enum은 열거형 타입 이라고 해서 서로 연관된 상수를 모아놓은 집합이다. )

위의 코드에서 String type을 바꿔볼텐데, enum의 타입이 male, female로 둘 중 하나로 고정되어야 한다고 가정해보자.

아래와 같이 Enum 타입을 만들 수 있다.
(타입의 이름은 원하는 대로 설정하면 된다.)

enum Type { male, female }
// enum 타입 이름 { 타입1, 타입2, ... }

class의 property는 아래와 같이 변경된다.

class Info {
  String name;
  int age;
  Type type;
  ...
}

마지막으로 생성자를 호출할 땐 어떻게 해야할까?

var zen = Info(name: 'zen', age: 26, type: Type.male)
    ..name = 'zen2'
    ..age = 30
    ..type = Type.female
    ..printInfo();

기존의 type을 초기화하는 곳을 enum 이름.타입으로 바꿔주면 된다.

enum { .. }에 들어가는 것은 타입의 이름이다.(=원하는 타입 이름)
문자열이면 안된다.


추상 클래스

추상 클래스는 다른 클래스들이 직접 구현해야 하는 메소드들을 모아논 일종의 청사진이다.

  • 추상 클래스로는 객체를 생성할 수 없다.
  • {}으로 무엇을 할지는 적지 않고, 단순히 메소드만 선언한다.
  • 메소드로 무엇을 할지는 추상 클래스를 구체화하는 클래스가 할 일이다.
abstract class Person {
  void eat(String food);
}

enum Type { male, female }

class Zen extends Person {
  void eat(String food) {
    print('Zen is eating $food');
  }
}

class Bibi extends Person {
  void eat(String food) {
    print('Aom is eating $food');
  }
}

void main() {
  var zen = Zen()
  ..eat('pizza');
  var bibi = Bibi()
  ..eat('chicken');
}

profile
데브코스 진행 중.. ~ 2024.03

0개의 댓글