dart语言学习笔记-2

默认值

如果变量未被初始化,变量的值为null

int lineCount;
assert(lineCount == null);

注:assert()的调用在生产阶段会被忽略

赋值

??=给空对象赋值

// Assign value to a
a = value;
// Assign value to b if b is null; otherwise, b stays the same
b ??= value;

final & const

final变量只能设值一次且需要在第一次使用时设值,const变量为编译期常量(隐式final)

注:实例变量可以为final,但不能为const。final的实例变量必须在构造器之前初始化,如变量声明、构造参数,或者构造器的初始化列表

final name = 'Bob'; // Without a type annotation
final String nickname = 'Bobby';

const变量的值为数字、字符串,或他们的计算结果

const bar = 1000000; // Unit of pressure (dynes/cm2)
const double atm = 1.01325 * bar; // Standard atmosphere

const值

var foo = const [];
final bar = const [];
const baz = []; // Equivalent to `const []`

你可以修改非final,非const的变量,即使他的值为const

foo = [1, 2, 3]; // Was const []

内建数据类型

numbers

只包含int和double类型,且int不大于64bits,double为64bit

int会自动转为double

double z = 1; // Equivalent to double z = 1.0.

strings

Dart的string是一串UTF-16编码的字符,可以用单引号或双引号来创建

var s1 = 'Single quotes work well for string literals.';
var s2 = "Double quotes work just as well.";
var s3 = 'It\'s easy to escape the string delimiter.';
var s4 = "It's even easier to use the other delimiter.";

如果变量为表达式,可通过${expression}在创建字符串时来引用,如果是变量可以省略{},对象的话会默认调用toString()方法

var s = 'string interpolation';

assert('Dart has $s, which is very handy.' ==
    'Dart has string interpolation, ' +
        'which is very handy.');
assert('That deserves all caps. ' +
        '${s.toUpperCase()} is very handy!' ==
    'That deserves all caps. ' +
        'STRING INTERPOLATION is very handy!');

字符串可以通过相邻或者+来拼接

var s1 = 'String '
    'concatenation'
    " works even over line breaks.";
assert(s1 ==
    'String concatenation works even over '
    'line breaks.');

var s2 = 'The + operator ' + 'works, as well.';
assert(s2 == 'The + operator works, as well.');

如果要创建的是多行的字符串(包含换行),用三个引号包裹即可

var s1 = '''
You can create
multi-line strings like this one.
''';

var s2 = """This is also a
multi-line string.""";

如果要创建原始的非转义字符串,需要用r开头(和python相同)

var s = r'In a raw string, not even \n gets special treatment.';

booleans(true/false)

Dart为类型安全,所以不能像javascript那样使用if (nonbooleanValue)assert (nonbooleanValue)

lists

List代表有序集合,在Dart中的数组即为List对象

//Dart推断list代表List,如果添加非int型对象会发出异常警告
var list = [1, 2, 3];

sets

Set代表无序集合

//Dart推断set代表Set,只能添加string对象
var halogens = {'fluorine', 'chlorine', 'bromine', 'iodine', 'astatine'};

创建一个空的set,需要指明类型,如

var names = {};
// Set names = {}; // This works, too.
// var names = {}; // Creates a map of Map, not a set.

注:小心创建了一个map对象
要创建一个编译期的常量,需要添加const前导

final constantSet =
    const {'fluorine', 'chlorine', 'bromine', 'iodine', 'astatine'};
// constantSet.add('helium'); // Uncommenting this causes an error.

maps

两种初始化方式

//方式1
var gifts = {
  // Key:    Value
  'first': 'partridge',
  'second': 'turtledoves',
  'fifth': 'golden rings'
};
//方式2
var nobleGases = Map();
nobleGases[2] = 'helium';
nobleGases[10] = 'neon';
nobleGases[18] = 'argon';

构建编译期的常量时,需要添加前导const

final constantMap = const {
  2: 'helium',
  10: 'neon',
  18: 'argon',
};

// constantMap[2] = 'Helium'; // Uncommenting this causes an error.

runes

代表UTF-32编码的字符串


fromCharCodes
main() {
  var clapping = '\u{1f44f}';
  print(clapping);
  print(clapping.codeUnits);
  print(clapping.runes.toList());
​
  Runes input = new Runes(
      '\u2665  \u{1f605}  \u{1f60e}  \u{1f47b}  \u{1f596}  \u{1f44d}');
  print(new String.fromCharCodes(input));
}

console output


[55357, 56399]
[128079]
♥          

当进行字符处理时,需要当心包含runes的情况,如

void main() {
  //一种情况
  var input = "Music \u{1f44d} for the win"; // Music  for the win
  
  print(input.split('').reversed.join()); // niw eht rof �� cisuM
  
  print(new String.fromCharCodes(input.runes.toList().reversed)); // niw eht rof  cisuM

  //另一种情况
  var input2 =  'Ame\u{301}lie'; // Amélie
  print(new String.fromCharCodes(input2.runes.toList().reversed)); // eiĺemA
}

symbols

Symbol对象代表声明的运算符或者标识符,你可能永远都不需要Symbol
通过#跟随标识符获取symbol

#radix
#bar

函数对象(Functions)

箭头表达式

bool isNoble(int atomicNumber) => _nobleGases[atomicNumber] != null;

注:=> expr;语法是{ return expr; }的简写,在=>之间只能是表达式,不能是其他如if

可选参数

Optional positional parameters

必选参数在前,可选参数在后

String say(String from, String msg, [String device]) {
  var result = '$from says $msg';
  if (device != null) {
    result = '$result with a $device';
  }
  return result;
}

assert(say('Bob', 'Howdy') == 'Bob says Howdy');

Optional named parameters

通过{param1, param2, ...}的格式命名参数,用@required标记为必选参数,通过参数名称传值( 即paramName: value)方式调用

/// Sets the [bold] and [hidden] flags ...
void enableFlags({bool bold, @required bool hidden}) {...}
//使用时
enableFlags(bold: true, hidden: false);

参数默认值

定义时通过=赋值,且默认值必须是编译期常量,未赋值默认为null

/// Sets the [bold] and [hidden] flags ...
void enableFlags({bool bold = false, bool hidden = false}) {...}

// bold will be true; hidden will be false.
enableFlags(bold: true);

main函数

任何app都必须包括一个顶级的main(),作为app的入口函数,main()必须返回void,并有一个可选的List参数。

void main() {
  querySelector('#sample_text_id')
    ..text = 'Click me!'
    ..onClick.listen(reverseText);
}

..语法是作为级联调用的

匿名函数

格式
([[Type] param1[, …]]) {
codeBlock;
};

var list = ['apples', 'bananas', 'oranges'];
list.forEach((item) {
  print('${list.indexOf(item)}: $item');
});

如果函数体只有一条语句,可以用箭头语法替换

list.forEach(
    (item) => print('${list.indexOf(item)}: $item'));

Lexical scope(词法范围)

Dart是一种词汇范围的语言,这意味着变量的范围是静态确定的,只需通过代码的布局。您可以“沿大括号向外”查看变量是否在范围内。

bool topLevel = true;

void main() {
  var insideMain = true;

  void myFunction() {
    var insideFunction = true;

    void nestedFunction() {
      var insideNestedFunction = true;

      assert(topLevel);
      assert(insideMain);
      assert(insideFunction);
      assert(insideNestedFunction);
    }
  }
}

Lexical closures(词法闭包)

closure(闭包)可以访问他所在的lexical scope(词法范围)的变量,即使被用到了在他原有的范围之外

/// Returns a function that adds [addBy] to the
/// function's argument.
Function makeAdder(num addBy) {
  return (num i) => addBy + i;
}

void main() {
  // Create a function that adds 2.
  var add2 = makeAdder(2);

  // Create a function that adds 4.
  var add4 = makeAdder(4);

  assert(add2(3) == 5);
  assert(add4(3) == 7);
}

特殊运算符

condition ? expr1 : expr2

如果condition为true,则调用expr1,否则调用expr2

expr1 ?? expr2

如果expr1非空,返回expr1的值,否则返回expr2的值

Cascade notation (..)

用前一个对象作为级联对象

final addressBook = (AddressBookBuilder()
      ..name = 'jenny'
      ..email = '[email protected]'
      ..phone = (PhoneNumberBuilder()
            ..number = '415-555-0100'
            ..label = 'home')
          .build())
    .build();

?.

.运算符类似,如foo?.bar,如果foo非空,返回foo.bar,否则返回null

控制语句

switch and case

switch语句可以比较integer,string,或者用==比较编译期常量。待比较的对象必须是同一个类(不能为子类),并且这个类不能复写了==。枚举类适合switch语句。

注:某些情况下break不可缺少

var command = 'OPEN';
switch (command) {
  case 'OPEN':
    executeOpen();
    // ERROR: Missing break

  case 'CLOSED':
    executeClosed();
    break;
}

支持空的case,此时允许穿透

var command = 'CLOSED';
switch (command) {
  case 'CLOSED': // Empty case falls through.
  case 'NOW_CLOSED':
    // Runs for both CLOSED and NOW_CLOSED.
    executeNowClosed();
    break;
}

如果真的需要穿透,需要借助continue语句

var command = 'CLOSED';
switch (command) {
  case 'CLOSED':
    executeClosed();
    continue nowClosed;
  // Continues executing at the nowClosed label.

  nowClosed:
  case 'NOW_CLOSED':
    // Runs for both CLOSED and NOW_CLOSED.
    executeNowClosed();
    break;
}

try/throw/rethrow/catch/finally

  1. Dart可以throw任何对象,不仅限于exception
  2. 在判断throw时,on或者catch都可以(也可以同时使用),用on表示只关心抛出的类型,用catch表示关心抛出的具体对象
  3. catch时,堆栈为可选参数,即第一个参数为抛出的对象,第二个为堆栈(StackTrace)堆栈
  4. 通过rethrow,重新抛出该异常
    捕获单个throw
try {
  breedMoreLlamas();
} on OutOfLlamasException {
  buyMoreLlamas();
}

捕获多个throw

try {
  breedMoreLlamas();
} on OutOfLlamasException {
  // A specific exception
  buyMoreLlamas();
} on Exception catch (e) {
  // Anything else that is an exception
  print('Unknown exception: $e');
} catch (e) {
  // No specified type, handles all
  print('Something really unknown: $e');
}

带堆栈,并继续抛出异常

try {
  // ···
} on Exception catch (e) {
  print('Exception details:\n $e');
} catch (e, s) {
  print('Exception details:\n $e');
  print('Stack trace:\n $s');
  rethrow;// Allow callers to see the exception.
}

你可能感兴趣的:(dart语言学习笔记-2)