[英]Dart Named constructor vs Static method what to prefer?
So after dart
made new
keyword optional,所以在
dart
使new
关键字可选之后,
we can initialize an object with exact same syntax but different internal implementation .我们可以使用完全相同的语法但不同的内部实现来初始化 object。
class Color {
int r = 0, g = 0, b = 0;
Color({this.r, this.b, this.g});
//Named constructors
Color.red() //Implementation
Color.cyan() //Implementation
// Static Initializers
static Color red() => //Initialze with parameter
static Color cyan() => //Initialze with parameter
}
We can use them like this regardless of being it a named constructor
or static method
:无论是
named constructor
还是static method
,我们都可以这样使用它们:
Color red = Color.red();
Color cyan = Color.cyan();
What is the place to use each of them?使用它们每个的地方是什么?
Constructors and static functions are different.构造函数和 static 函数不同。 You usually create a named constructor that returns an instance of an object with some predefined values.
您通常会创建一个命名构造函数,该构造函数返回具有一些预定义值的 object 实例。 For example, you have a class called
Person
which stores Name
and Job
.例如,您有一个名为
Person
的 class 存储Name
和Job
。 You can create this named constructer Person.doctor(name)
which you will return a Person
object with Job = 'doctor'
您可以创建这个命名构造
Person.doctor(name)
,您将返回一个Person
object ,其中Job = 'doctor'
class Person{
final name;
final job;
Person(this.name, this.job);
Person.doctor(this.name, {this.job = "doctor"});
}
Static functions or variable persists on all the instance of a class. Static 函数或变量持续存在于 class 的所有实例上。 Let us say,
Person
has a static variable called count
.假设,
Person
有一个名为count
的 static 变量。 You increment the count variable whenever an instance of Person
is created.每当创建
Person
的实例时,就增加 count 变量。 You can call Person.count
anywhere later in your code to get the value of count
(Number of instances of Person
)您可以稍后在代码中的任何位置调用
Person.count
以获取count
的值( Person
的实例数)
class Person{
final name;
final job;
static int count;
Person(this.name, this.job){
count++;
}
Person.doctor(this.name, {this.job = "doctor"});
}
In practice there is little difference between a factory constructor and a static method.实际上,工厂构造函数和 static 方法之间几乎没有区别。
For a generic class, it changes where you can (and must) write a type parameter:对于通用 class,它会更改您可以(并且必须)编写类型参数的位置:
class Box<T> {
T value;
Box._(this.value);
factory Box.withValue(this.value) => Box<T>._(value);
static Box<T> fromValue<T>(T value) => Box<T>._(value);
}
...
var box1 = Box<int>.withValue(1);
var box2 = Box.fromValue<int>(2);
So, for generic classes, factory constructors are often what you want.因此,对于泛型类,工厂构造函数通常是您想要的。 They have the most pleasant syntax.
他们有最令人愉快的语法。
For non-generic classes, there is very little difference, so it's mainly about signaling intent.对于非泛型类,差别很小,所以主要是关于信号意图。 And deciding which category the name goes into in the DartDoc.
并决定名称在 DartDoc 中属于哪个类别。
If the main objective of the function is to create a new object, make it a constructor.如果 function 的主要目标是创建一个新的 object,则使其成为构造函数。
If the main objective is to do some computation and eventually return an object (even if it's a new object), make it a static function.如果主要目标是进行一些计算并最终返回 object(即使它是一个新对象),请将其设为 static function。 That's why
parse
methods are generally static functions.这就是为什么
parse
方法通常是 static 函数。
In short, do what feels right for your API.简而言之,做适合您的 API 的事情。
Another benefit of the distinction between named constructor
and static function
is that in the documentation generated the function will be either filed in the construction section or the methods section, which further makes it's intentions clearer to the reader. named constructor
和static function
之间区别的另一个好处是,在生成的文档中 function 将进一步归档在构造部分或方法部分中,以便读者更清楚地了解。
A person looking for a constructor in the constructor section of the documentation will easily discover the named constructors as opposed to having to also dig through the static functions section too.在文档的构造函数部分中寻找构造函数的人将很容易发现命名的构造函数,而不必也挖掘 static 函数部分。
Another very useful feature of static class methods is that you can make them asynchronous, ie wait for full initialisation in case this depends on some asynchronous operation: static class 方法的另一个非常有用的特性是您可以使它们异步,即等待完全初始化,以防这取决于一些异步操作:
Future<double> getCurrentPrice(String ticker) async {
double price;
// for example, fetch current price from API
price = 582.18;
return price;
}
class Stock {
String ticker;
double currentPrice=0.0;
Stock._(this.ticker);
static Future<Stock> stockWithCurrentPrice(String ticker) async {
Stock stock = Stock._(ticker);
stock.currentPrice = await getCurrentPrice (ticker);
return stock;
}
}
void main() async {
Stock stock = await Stock.stockWithCurrentPrice('AAPL');
print ('${stock.ticker}: ${stock.currentPrice}');
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.