Відповіді:
На сайті дартса є публікація, і це досить добре пояснює.
Фінал:
"final" означає однозначне призначення: остаточна змінна або поле має мати ініціалізатор. Після призначення значення значення остаточної змінної не можна змінити. остаточний змінює змінні .
Const:
"const" має значення, яке є дещо складнішим і тонкішим у Dart. const змінює значення . Ви можете використовувати його під час створення колекцій, як const [1, 2, 3], і при побудові об'єктів (замість нових), таких як Const Point (2, 3). Тут const означає, що весь глибокий стан об'єкта може бути визначений повністю під час компіляції і що об'єкт буде застигнутим і повністю незмінним.
Об'єкти Const мають кілька цікавих властивостей та обмежень:
Вони повинні бути створені з даних, які можна обчислити під час компіляції. Об'єкт const не має доступу до всього, що вам потрібно було б обчислити під час виконання. 1 + 2 - допустимий вираз const, але новий DateTime.now () - ні.
Вони глибоко, транзитивно незмінні. Якщо у вас є остаточне поле, що містить колекцію, ця збірка все ще може бути зміненою. Якщо у вас є колекція const, все в ній також повинно бути const, рекурсивно.
Вони канонізовані . Це щось на зразок інтернування інтерфейсу: для будь-якого заданого значення const один об'єкт const буде створений та повторно використаний незалежно від того, скільки разів виражаються вирази const.
Const:
Якщо значення, яке ви маєте, обчислюється під час виконання ( new DateTime.now()
наприклад), ви не можете використовувати const для нього. Однак, якщо значення відомо під час компіляції ( const a = 1;
), тоді вам слід скористатися const
над final
. Є ще 2 великі відмінності між const
та final
. По-перше, якщо ви використовуєте const
, ви повинні оголосити це як static const
просто, а не просто const
. По-друге, якщо у вас є const
колекція, все, що знаходиться всередині цього є const
. Якщо у вас є final
колекція, все всередині цього немає final
.
Остаточний: його
final
слід використовувати, const
якщо ви не знаєте значення під час компіляції, і воно буде обчислено / схоплено під час виконання. Якщо ви хочете відповідь HTTP, яку неможливо змінити, якщо ви хочете отримати щось із бази даних, або якщо ви хочете прочитати з локального файлу, використовуйте final
. Все, що не відомо на час компіляції, має final
закінчитися const
.
Незважаючи на все сказане, обидва const
і final
не можуть бути перепризначені, але поля в final
об'єкті, доки їх немає const
або final
можуть бути перепризначені (на відміну від const
).
const
і коли final
? Чи знаєте ви якийсь варіант використання цього модифікатора?
Значення повинно бути відоме під час компіляції , його
const birthday = "2008/12/26"
неможливо змінити після ініціалізації.
Значення має бути відомо , в перспективі часу ,
final birthday = getBirthDateFromDB()
не може бути змінено після ініціалізації.
Зведені відповіді @Meyi і @ faisal-naseer та порівняння з невеликим програмуванням.
Ключове слово const використовується для створення змінної для зберігання постійного значення часу компіляції . Постійна величина часу компіляції - це значення, яке буде постійним при компілюванні :-)
Наприклад 5
, константа часу компіляції. Хоча DateTime.now()
це не константа часу компіляції. Тому що цей метод поверне час, коли рядок виконується під час виконання. Таким чином , ми не можемо привласнити DateTime.now()
до const
змінної.
const a = 5;
// Uncommenting below statement will cause compile time error.
// Because we can't able to assign a runtime value to a const variable
// const b = DateTime.now();
Потрібно ініціалізувати в одному рядку .
const a = 5;
// Uncommenting below 2 statement will cause compilation error.
// Because const variable must be initialized at the same line.
// const b;
// b = 6;
Усі заяви, зазначені нижче, є прийнятними.
// Without type or var
const a = 5;
// With a type
const int b = 5;
// With var
const var c = 6;
Змінна const рівня класу повинна бути ініціалізована як нижче.
Class A {
static const a = 5;
}
Змінна const рівня екземпляра неможлива .
Class A {
// Uncommenting below statement will give compilation error.
// Because const is not possible to be used with instance level
// variable.
// const a = 5;
}
Інше основне використання const
використовується для того, щоб зробити об'єкт непорушним . Щоб зробити об’єкт класу незмінним, нам потрібно використовувати ключове слово const з конструктором і зробити всі поля такими, як зазначено нижче.
Class A {
final a, b;
const A(this.a, this.b);
}
void main () {
// There is no way to change a field of object once it's
// initialized.
const immutableObja = const A(5, 6);
// Uncommenting below statement will give compilation error.
// Because you are trying to reinitialize a const variable
// with other value
// immutableObja = const A(7, 9);
// But the below one is not the same. Because we are mentioning objA
// is a variable of a class A. Not const. So we can able to assign
// another object of class A to objA.
A objA = const A(8, 9);
// Below statement is acceptable.
objA = const A(10, 11);
}
ми можемо використовувати ключове слово const до списку .
const a = const [] - змінна, a
ініціалізована як така, const
що містить перелік const
об'єктів (тобто список повинен містити лише константи часу компіляції та незмінні об'єкти). Тому ми не можемо призначити a
інший список .
var a = const [] - a
Ініціалізованаvar
const
змінна , яка містить об'єкти списку . Таким чином ми можемо призначити інший список зміннійa
.
Class A {
final a, b;
const A(this.a, this.b);
}
class B {
B(){ // Doing something }
}
void main() {
const constantListOfInt = const [5, 6, 7,
// Uncommenting below statement give compilation error.
// Because we are trying to add a runtime value
// to a constant list
// DateTime.now().millisecondsSinceEpoch
];
const constantListOfConstantObjA = const [
A(5, 6),
A(55, 88),
A(100, 9),
];
// Uncommenting below 2 statements will give compilation error.
// Because we are trying to reinitialize with a new list.
// constantListOfInt = [8, 9, 10];
// constantListOfConstantObjA = const[A(55, 77)];
// But the following lines are little different. Because we are just
// trying to assign a list of constant values to a variable. Which
// is acceptable
var variableWithConstantList = const [5, 6, 7];
variableWithConstantList = const [10, 11, 15];
var variableOfConstantListOfObjA = const [A(5, 8), A(7, 9), A(10, 4)];
variableWithConstantList = const [A(9, 10)];
}
Остаточне ключове слово також використовується для того, щоб змінна містила постійне значення . Після ініціалізації ми не зможемо змінити значення.
final a = 5;
// Uncommenting below statement will give compilation error.
// Because a is declared as final.
// a = 6;
Усі заяви, зазначені нижче, є прийнятними.
// Without type or var
final a = 5;
// With a type
final int b = 5;
// With var
final var c = 6;
Може призначити значення часу виконання .
// DateTime.now() will return the time when the line is getting
// executed. Which is a runtime value.
final a = DateTime.now();
var b = 5;
final c = b;
Кінцева змінна рівня класу повинна бути ініціалізована в одному рядку.
Class A {
static final a = 5;
static final b = DateTime.now();
}
Кінцеву змінну рівня екземпляра необхідно ініціалізувати в тому ж рядку або в ініціалізації конструктора. Значення буде збережено в пам'яті, коли об’єкт створений.
Class A {
final a = 5;
}
// Constructor with a parameter.
Class B {
final b;
B(this.b);
}
// Constructor with multiple parameter.
Class C {
final c;
C(this.c, int d) {
// Do something with d
}
}
void main() {
A objA = new A();
B objB = new B(5);
C objC = new C(5, 6);
}
Призначення списку .
final a = [5, 6, 7, 5.6, A()];
// Uncommenting Below statement will give compilation error.
// Because we are trying to reinitialize the object with another list.
// a = [9.9, 10, B()];
Подовження відповіді від @Meyi
biggestNumberOndice
лише тоді, значення буде ініціалізовано і буде призначено пам'ять).const є внутрішньо остаточним за своєю суттю, але головна відмінність полягає в тому, що його константа часу компіляції, яка ініціалізується під час компіляції, навіть якщо ви не використовуєте її значення, вона буде ініціалізована і займе місце в пам'яті.
Змінна від класів може бути остаточною, але не постійною, і якщо ви хочете константа на рівні класу, зробіть це статичним const.
Код:
void main() {
// final demonstration
final biggestNumberOndice = '6';
// biggestNumberOndice = '8'; // Throws an error for reinitialization
// const
const smallestNumberOnDice = 1;
}
class TestClass {
final biggestNumberOndice = '6';
//const smallestNumberOnDice = 1; //Throws an error
//Error . only static fields can be declared as constants.
static const smallestNumberOnDice = 1;
}
І те, final
і const
інше запобігає переназначенню змінної (подібно до того, як final
працює в Java або як const
працює в JavaScript).
Різниця пов'язана з тим, як розподіляється пам'ять. Пам'ять виділяється для final
змінної під час виконання, а для const
змінної - під час компіляції. final
Модифікатор повинен бути більш широко використовується, тому що багато програмні змінні не потрібна пам'ять , так як логіка програми не буде вимагати їх ініціалізації. Зі const
змінною ви в основному говорите комп'ютеру: "Ей, мені потрібна пам'ять для цієї змінної вперед, тому що я знаю, що мені це потрібно".
Мислення про них таким чином полегшує розуміння відмінностей у їх синтаксичному використанні. Головним чином, що final
змінна може бути змінною екземпляра, але const
повинна бути static
змінною у класі. Це відбувається тому, що змінні екземплярів створюються під час виконання, а const
змінні - за визначенням - ні. Таким чином, const
змінні класу повинні бути static
, а це означає, що одна копія цієї змінної існує в класі, незалежно від того, чи є цей клас примірником.
Це відео розбиває його досить просто: https://www.youtube.com/watch?v=9ZZL3iyf4Vk
Ця стаття заглиблюється і пояснює дуже важливу семантичну різницю між цими двома, тобто final
змінює змінні та const
модифікує значення, що по суті зводиться до лише можливості ініціалізації const
значень, які можна отримати в момент компіляції.
https://news.dartlang.org/2012/06/const-static-final-oh-my.html
Якщо ви їдете з , C++
то const
в Dart
це constexpr
в C++
і final
в Dart
це const
в C++
.
Сказане стосується лише примітивних типів. Однак у Dart
позначених об'єктах final
є змінними з точки зору його членів.
const
в C ++ майже завжди використовується для вказівки, що об'єкт не може бути змінений через певну посилання або покажчик. final
у Dart не перешкоджає мутації об'єкта через цю змінну.
Коли використовувати яке ключове слово?
Простий приклад для обох: Використовуйте final: Якщо ви не знаєте, яке значення буде в час компіляції. Наприклад, коли вам потрібно буде отримати дані з API, це відбувається під час запуску вашого коду.
Використовуйте const: Якщо ви впевнені, що значення не буде змінено під час запуску коду. Наприклад, коли ви оголошуєте речення, яке завжди залишається однаковим.
https://itnext.io/difference-between-const-and-final-in-dart-78c129d0c573
const
: stackoverflow.com/questions/51576209 / ... і простому explonation доfinal
постійний (не може перепризначення або правонаступник після створення з остаточним ключовим словом) , і ви повинні ініціалізувати її один раз.