有没有更好的方法来使用 dart 语言中的 for 循环读取字符串中的值

Is there better way to read values in a string using for loop in dart language

我正在尝试编写一段代码,要求用户输入一个字符串并打印出该字符串是否为回文。

当代码执行时,它直接转到 print 语句,for 循环不会进入字符串并比较值。

  print("Enter a word to check for palindrome: ");
  String word = stdin.readLineSync()!;
  List<String> palindrome = [word];
  var flag = 0;

  //var len = palindrome.length;

 for (int i = 0; i < palindrome.length; i++) {
    if (palindrome[i] != palindrome[palindrome.length - i - 1]) {
      flag = 1;
      break;
    }
  }

  if (flag == 0) 
  {
    print("$palindrome is palindrome.");
  } else 
  {
    print("$palindrome is not palindrome.");
  }

你可以检查一下

word == word.split('').reversed.join('')

你的问题是你写的:

List<String> palindrome = [word];

然后检查palindrome是否是回文作为元素列表。因为它只有一个元素,所以它是一个等于自身的词。你永远不会检查 word 是否是回文。

您可能想改为检查字符串的各个字符是否形成回文。 如果将该行更改为:

String palindrome = word;

那么您的代码将执行此操作。

但是,对于早期编码练习以外的任何事情,这种方法都太天真了,无法在现实世界中工作,因为现实世界中并非所有字母都是 ASCII,也不是所有字符都由单个代码单元。

仅使用代码单元的问题在于像 "" 这样的字符串又名。 “\u{1f602}”应该是一个回文(它只包含一个“字符”),但实际的字符串表示是 "\uD83d\uDE02",这在代码单元级别不是回文(并且交换代码单位是无效的 UTF-16)。 因此,要认识到这一点,您必须将这两个代码单元视为一个字符。

至少,我会使用 Stringrunes getter 来访问代码 points 以及是否检查那些形成回文。那么如果字符串包含简单的非基本多语言平面字符,结果仍然正确,这些字符在 Dart 中由两个代码单元表示:

var r1 = word.runes.iterator;
var r2 = word.runes.iterator..reset(word.length);
while (r1.moveNext() && r2.movePrevious()) {
  if (r1.rawIndex >= r2.rawIndex) break; // Reached the middle.
  if (r1.current != r2.current) {
    flag = 1;
    break;
  }
}

对于真实世界的文本,我建议使用 characters package 访问文本的 字形簇 ,它可以包含多个代码点。

同样的问题:字符串 "️‍" 看起来像一个字符,因此是一个回文,但实际上它是一个 "️\u200D" (白旗,零宽度连接符,彩虹)序列,只是像许多其他表情符号一样,是由多个部分创建的。 字符包会将彩虹旗识别为一个“字符”。

import "package:characters/characters.dart";
...
  var r1 = words.characters.iterator;
  var r2 = words.characters.iteratorAtEnd;
  while (r1.moveNext() && r2.moveBack()) {
    if (r1.stringBeforeLength >= r2.stringBeforeLength) {
      break; // Reached the middle.
    }
    if (r1.current != r2.current) {
      flag = 1;
      break;
    }
  }

您仍然可以 运行 解决 Unicode 规范化问题。 字符串 "éé" 看起来像一个回文,但它实际上是 "ée\u0301",它包含两个 不同的 表示相同的重音 e 字符,一个作为一个字符,一个作为 e ,后面有一个组合重音。 characters 包会将它们报告为不同的代码点序列,并且不知道它们代表相同的 character.