如何在 Dart 中逐个字符地迭代字符串?

Posted

技术标签:

【中文标题】如何在 Dart 中逐个字符地迭代字符串?【英文标题】:How to iterate over a String, char by char, in Dart? 【发布时间】:2012-03-06 09:52:01 【问题描述】:

我没有看到 Dart 字符串被视为字符列表。我假设我必须使用 for 循环,这会很蹩脚。

【问题讨论】:

【参考方案1】:

用颤振Characters Class

import 'package:flutter/material.dart';
var characters = aString.characters;

【讨论】:

【参考方案2】:

正确迭代String的扩展:

extension on String 

  /// To iterate a [String]: `"Hello".iterable()`
  Iterable<String> iterable() sync* 
    for (var i = 0; i < length; i++) 
      yield this[i];
    

像这样使用它:

expect("Hello".iterable(), ["H", "e", "l", "l", "o"]);

但是,如果您添加 Characters package:

import "package:characters/characters.dart"; 

然后您可以使用简单字符或 Unicode 字形正确地迭代 String 的扩展:

extension on String 

  /// To iterate a [String]: `"Hello".iterable()`
  /// This will use simple characters. If you want to use Unicode Grapheme
  /// from the [Characters] library, passa [chars] true.
  Iterable<String> iterable(bool unicode = false) sync* 
    if (unicode) 
      var iterator = Characters(this).iterator;
      while (iterator.moveNext()) 
        yield iterator.current;
      
     else
      for (var i = 0; i < length; i++) 
        yield this[i];
      
  

为了证明它有效:

  test('String.iterable()', () 
    expect("Hello".iterable(), ["H", "e", "l", "l", "o"]);
    expect("Hello".iterable(unicode: true), ["H", "e", "l", "l", "o"]);

    expect("?".iterable().length, 2);
    expect("?".iterable().map((s) => s.codeUnitAt(0)), [55357, 56842]);

    expect("?".iterable(unicode: true).length, 1);
    expect("?".iterable(unicode: true), ["?"]);
  );

【讨论】:

【参考方案3】:

extension on String 
  //toArray1 method
  List toArray1() 
    List items = [];
    for (var i = 0; i < this.length; i++) 
      items.add(this[i]);
    
    return items;
  

  //toArray2 method
  List toArray2() 
    List items = [];
    this.split("").forEach((item) => items.add(item));
    return items;
  


main(List<String> args) 
  var str = "hello world hello world hello world hello world hello world";
  final stopwatch1 = Stopwatch()..start();
  print(str.toArray1());
  print('str.toArray1() executed in $stopwatch1.elapsed');

  final stopwatch2 = Stopwatch()..start();
  print(str.toArray2());
  print('str.toArray2() executed in $stopwatch2.elapsed');




以上是使用 for 循环和 foreach 的示例,但我测试的结果是,foreach 的工作方式比 for 循环快。对不起,如果我错了,但这是我的测试。

【讨论】:

【参考方案4】:

您还可以使用split method 生成List 字符。

input.split('').forEach((ch) => print(ch));

【讨论】:

【参考方案5】:

另一种实现方式(使用基本多语言平面之外的字符):

"A string".runes.forEach((int rune) 
  var character=new String.fromCharCode(rune);
  print(character);
);

【讨论】:

从 Dart 2.7.0 开始,可以使用包characters:pub.dev/packages/characters。 BonusPoint:: getter codeUnits 也可以用来代替符文,如:"A string".codeUnits.forEach((int c) var character=new String.fromCharCode(c); print(character); ); String.codeUnits 仅处理 UTF-16 代码点,而 String.runes 处理 Unicode 代码点(UTF-8、UTF-16、UTF-32)。一个字符可以用 2 个 UTF-16 代码点(即代理对)表示,但只能用 1 个符文表示。【参考方案6】:

不幸的是,strings 目前不可迭代,因此您必须使用这样的 for 循环

for(int i=0; i<s.length; i++) 
  var char = s[i];

请注意,Dart 没有字符类,因此 string[index] 将返回另一个字符串。

【讨论】:

警告:对于一些罕见的外语,循环无法按预期工作。 length 属性和 [] 运算符指的是 UTF-16 代码单元,而不是字符。某些字符可以使用 2 个 UTF-16 代码单元。

以上是关于如何在 Dart 中逐个字符地迭代字符串?的主要内容,如果未能解决你的问题,请参考以下文章

如何将字符串(逐个字符)推入字符串向量

Python中 appendextendinsertadd 区别

Dart String 可迭代接口

Android开发Dart 的 String 字符串的常用方法

如何在 HTML5 画布上逐个像素地绘制

如何实现占位符文本在 UITextField 中逐个字符消失