Структури

Одним із способів визначення складених або спеціалізованих типів у D є визначення їх через struct:

struct Person {
    int age;
    int height;
    float ageXHeight;
}

Структури завжди створюються у стеці (якщо не створенi за допомогою new) і копіюються за значенням при присвоєнні чи при передачі у якості параметру фукнції.

auto p = Person(30, 180, 3.1415);
auto t = p; // створюється копія

Коли створюється новий об'єкт типу struct, його члени можуть бути ініціалізовані у тому ж порядку, в якому вони визначені у struct. Користувач сам може визначити конструктор за допомогою ключового слова this(...). Щоб уникнути конфлікту імен, поточний екземпляр структури може бути явно доступний за допомогою ключового слова this:

struct Person {
    this(int age, int height) {
        this.age = age;
        this.height = height;
        this.ageXHeight = cast(float)age * height;
    }
        ...

Person p(30, 180); // iнiцiалiзацiя
p = Person(30, 180);  // призначення новим екземпляром

struct може містити будь-яку кількість функцій. За замовчуванням усi вони мають рiвень захисту public і доступнi ззовні. Вони можуть також мати рiвень захисту private. У цьому випадку їх зможуть викликати лише функції тієї ж структури, або інши код того ж самого модуля.

struct Person {
    void doStuff() {
        ...
    private void privateStuff() {
        ...

p.doStuff(); // викликає метод doStuff
p.privateStuff(); // заборонено

Функції сonst

Якщо функція оголошується з ключовим словом const, то буде заборонено змінювати будь-який її член. Це забезпечується компілятором. Функція з ключовим словом const може бути викликаною з будь-якого const або immutable об'єкта, і є гарантія, що ця функція не змінить стан об'єкта.

Статичнi функції

Якщо функція оголошена як static, вона буде викликатися без екземпляра об'єкта (наприклад - Person.myStatic()), але їй заборонений доступ до будь-яких не-static членів. static функцію можна використовувати, якщо вам не потрібний доступ до полів об'єкту, але логічно його розмістити у тому ж класі. Також можна використовувати статичні функції для реалізації функціональності, якій не потрібно створювати об'єкт. Наприклад, сінглтони (або Singleton, які існують лише в одному екземплярi) використовують static.

Успадкування

Зверніть увагу, що struct не може успадковуватись від іншого struct. Iєрархiї типів можуть бути побудовані тільки з використанням класів, з якими ми ознайомимось у наступному розділі. Однак з alias this або mixins можна легко досягти поліморфного успадкування.

Додатково

Вправа

Маючи struct Vector3 реалізувати наступні функції і зробити так, щоб приклад програми виконувався успішно:

  • length() - повертає довжину вектора.
  • dot(Vector3) - повертає скалярний добуток двох векторiв.
  • toString() - повертає рядкове уявлення вектору. Функцiя std.string.format повертає рядок використовуючи printf-подiбний синтаксис: format("MyInt = %d", myInt). Більш детально рядки будуть пояснені у наступих розділах.

rdmd playground.d