Как положить и отсортировать слова в NSCountingSet в Swift? - PullRequest
0 голосов
/ 26 марта 2020

Я пытаюсь получить наиболее повторяющееся слово из строки с этим кодом.

let text = """
  aa bb aa bb aa bb cc dd dd cc zz zz cc dd zz
  """
  let words = text.unicodeScalars.split(omittingEmptySubsequences: true, whereSeparator: { !CharacterSet.alphanumerics.contains($0) })
  .map { String($0) }
  let wordSet = NSCountedSet(array: words)
  let sorted = wordSet.sorted { wordSet.count(for: $0) > wordSet.count(for: $1) }
print(sorted.prefix(3))

результат равен

[cc, dd, aa]

В настоящее время он помещает все слова, даже если это один символ.

Я собираюсь сделать следующее:

  1. поместить слово в NSCountingSet, которое имеет более одного символа.
  2. , если слова в NSCountingSet имеют одинаковое количество, сортируйте их по алфавиту. (желаемый результат - *, 1025 *, дд)

И если это возможно ..

пропустить части речи из строки, такие как «и, как, из, к, это, в, кто» .... et c

1 Ответ

1 голос
/ 26 марта 2020

Давайте рассмотрим эту строку:

let text = """
      She was young the way an actual young person is young.
      """

Вы можете использовать linguisti c tagger:

import NaturalLanguage

let options = NSLinguisticTagger.Options.omitWhitespace.rawValue
let tagger = NSLinguisticTagger(tagSchemes: NSLinguisticTagger.availableTagSchemes(forLanguage: "en"), options: Int(options))

Для подсчета кратности каждого слова я буду использовать словарь :

var dict = [String : Int]()

Давайте определим принятые теги linguisti c (вы измените их по своему вкусу):

let acceptedtags: Set = ["Verb", "Noun", "Adjective"]

Теперь давайте разберем строку, используя тег linguisti c :

let range = NSRange(location: 0, length: text.utf16.count)
tagger.string = text

tagger.enumerateTags(
    in: range,
    scheme: .nameTypeOrLexicalClass,
    options: NSLinguisticTagger.Options(rawValue: options),
    using: { tag, tokenRange, sentenceRange, stop in
        guard let range = Range(tokenRange, in: text)
            else { return }

        let token = String(text[range]).lowercased()

        if let tagValue = tag?.rawValue,
            acceptedtags.contains(tagValue)
        {
            dict[token, default: 0] += 1
        }

        // print(String(describing: tag) + ": \(token)")
})

Теперь у dict есть нужные слова с их кратностью

print("dict =", dict)

Как вы можете видеть, словарь является незарегистрированной коллекцией. Теперь давайте введем закон и порядок:

let ordered = dict.sorted {
    ($0.value, $1.key) > ($1.value, $0.key)
}

Теперь давайте возьмем только ключи *:

let mostFrequent = ordered.map { $0.key }

и напечатаем три наиболее часто встречающихся слова:

print("top three =", mostFrequent.prefix(3))

Чтобы получить наиболее часто встречающиеся слова, было бы более эффективно использовать структуру данных Heap (или Tr ie) вместо того, чтобы иметь sh каждое слово, сортировать их все по частоте и затем добавлять префиксы. Это должно быть веселое упражнение.

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