Есть ли способ сортировки списков строк по номерам внутри строк? - PullRequest
0 голосов
/ 26 апреля 2020

Есть ли способ отсортировать что-то вроде:

List<String> hi = ['1hi', '2hi','5hi', '3hi', '4hi'];

к этому?

['1hi', '2hi','3hi', '4hi', '5hi']

Ответы [ 2 ]

1 голос
/ 26 апреля 2020

Простой вызов List<String>.sort() сам по себе лексический сортировка . То есть ваши строки будут отсортированы в порядке кодировки символов, а '10' будет отсортирован до '2'. Как правило, этого не ожидается.

Лексическая сортировка будет работать , если ваши числа имеют ведущие 0 s, чтобы гарантировать, что все числа имеют одинаковое количество цифр. Однако, если количество цифр является переменным, вам потребуется разобрать значения чисел для сортировки. Более общий подход заключается в предоставлении обратного вызова к .sort(), чтобы сообщить ему, как определить относительный порядок двух элементов.

К счастью, package:collection имеет compareNatural функция, которая может сделать это за вас:

import 'package:collection/collection.dart';

List<String> hi = ['1hi', '2hi','5hi', '3hi', '4hi'];
hi.sort(compareNatural);

Если ваша ситуация немного сложнее и compareNatural не делает то, что вы хотите, более общий подход - сделать .sort() callback выполняет синтаксический анализ, например, с помощью регулярного выражения:

/// Returns the integer prefix from a string.
///
/// Returns null if no integer prefix is found.
int parseIntPrefix(String s) {
  var re = RegExp(r'(-?[0-9]+).*');
  var match = re.firstMatch(s);
  if (match == null) {
    return null;
  }
  return int.parse(match.group(1));
}

int compareIntPrefixes(String a, String b) {
  var aValue = parseIntPrefix(a);
  var bValue = parseIntPrefix(b);
  if (aValue != null && bValue != null) {
    return aValue - bValue;
  }

  if (aValue == null && bValue == null) {
    // If neither string has an integer prefix, sort the strings lexically.
    return a.compareTo(b);
  }

  // Sort strings with integer prefixes before strings without.
  if (aValue == null) {
    return 1;
  } else {
    return -1;
  }
}

void main() {
  List<String> hi = ['1hi', '2hi','5hi', '3hi', '4hi'];
  hi.sort(compareIntPrefixes);
}
1 голос
/ 26 апреля 2020

Вы можете отсортировать список следующим образом:

hi.sort();

(потому что числа сортируются перед буквами при его реализации)

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...