Я пытаюсь проанализировать предложение и совершить действие в зависимости от этого. Вот примеры предложений, полученных при распознавании речи. Я написал пару предложений, потому что мы точно не знаем, что скажет пользователь, и правильно ли он говорит.
var str = "20 minutes to take a shower"
var sentence = "seven minutes to make 10 last homeworks"
var sentence2 = "strum guitar for 15 minutes"
var plans = "launch with friend 12:15, then drawing lesson"
Я хочу извлечь «20 минут»; назначьте его для timeValue и запустите таймер. Кроме того, чтобы назначить задачу taskValue, чтобы представить задачу, которую я выполняю. (Я думал получить значение задачи, удалив «20 минут» из начального предложения).
- Как вы думаете, как лучше всего работать со строкой, которую мне нужно проанализировать? Я думал найти диапазоны индексов, а затем вырезать / копировать с помощью индексов, но
Формат возвращаемых индексов такой: и я не знаю, как извлечь количество индекс. (В данном случае: от 0 до 10)
{0, 10} { [0-9] {1,} минут 0x1}
Как зажечь таймер? Мы должны убедиться, что дана правильная команда. И когда мы получим timeValue и taskValue обратно, как тогда нам запустить таймер? (Весь процесс был следующим: пользователь нажимает кнопку -> пользователь говорит -> распознается речь (и отображается на метке экрана) -> предложение анализируется (?) -> запускается таймер (?) И задача отображается в метке (?)) Каковы ваши рекомендации по архитектуре системы анализа речи. Может быть, вы знаете какие-нибудь статьи об этом c?
Вот лог c для обнаружения речи.
var timeValue: Int = Int()
var taskValue: String = ""
func stringDeduction(of inputText: String) -> (Int?, String?) {
let pattern = "[0-9]{1,} minutes"
let regexOptions: NSRegularExpression.Options = [.caseInsensitive]
let matchingOptions: NSRegularExpression.MatchingOptions = [.reportCompletion]
// TODO - catch errors with regex
let regex = try! NSRegularExpression(pattern: pattern, options: regexOptions)
// } catch {
// print("error in regex")
// }
let range = NSRange(location: 0, length: inputText.utf8.count)
// \d - matches any digit
// Pattern for time format like this 00:00
//let patternForTime = "[0-9]{1,}:[0-9]{1,2}"
if let matchIndex = regex.firstMatch(in: inputText, options: matchingOptions, range: range) {
print(matchIndex)
} else {
print("No match.")
}
// check whether the string matches and print one of two messages
if let match = regex.firstMatch(in: inputText, range: NSRange(location: 0, length: inputText.utf8.count)) {
print("*: Match!")
} else {
print("*: No match.")
}
/* Question - how to use "mathces" properly?!
if let match = regex.matches(in: testString, options: .reportCompletion ,range: NSRange(location: 0, length: testString.utf8.count)) {
print("*: Match!")
print(match)
} else {
print("*: No match.")
}
*/
func matches(for regex: String, in text: String) -> [String] {
do {
let regex = try NSRegularExpression(pattern: regex)
let results = regex.matches(in: text, options: [], range: NSRange(text.startIndex..., in: text))
return results.map {
String(text[Range($0.range, in: text)!])
}
} catch {
print("invalid regex")
return []
}
}
var task = regex.stringByReplacingMatches(in: inputText, options: .withoutAnchoringBounds, range: range, withTemplate: "")
//var taskMutableString = NSMutableString(string: str)
//regex.replaceMatches(in: taskMutableString, options: .withoutAnchoringBounds, range: range, withTemplate: "")
//taskMutableString
var timeStringArray = matches(for: pattern, in: inputText)
var timeString = timeStringArray[0]
let time = Int(timeString.replacingOccurrences(of: " minutes", with: ""))
timeValue = time ?? Int()
taskValue = task.replacingOccurrences(of: "to" , with: "", options: .caseInsensitive, range: task.startIndex..<task.index(task.startIndex, offsetBy: 4))
let taskReturn = taskValue
return (time, taskReturn)
// the regex ^[ \t]+|[ \t]+$ matches excess whitespace at the beginning or end of a line.
// what regex, or string method matches exess whitespace at the beginning of a line
}
Вот расширение для работы со строкой, как с массив. Вот так: - str [0..2]
extension String {
subscript (bounds: CountableClosedRange<Int>) -> String {
let start = index(startIndex, offsetBy: bounds.lowerBound)
let end = index(startIndex, offsetBy: bounds.upperBound)
return String(self[start...end])
}
subscript (bounds: CountableRange<Int>) -> String {
let start = index(startIndex, offsetBy: bounds.lowerBound)
let end = index(startIndex, offsetBy: bounds.upperBound)
return String(self[start..<end])
}
}
Вот еще один подход, который я пробовал: (Хотя это не кажется хорошим)
let timeArray = ["one minute", "two minutes", "three minutes", "four minutes", "five minutes", "six minutes", "seven minutes", "eight minutes", "nine minutes"]
let timeValueCheck = "Answer: \(sentence.containsAny(of: timeArray) ?? "doesn't contain")"
//Dividing String into words
let abc: [String] = str.components(separatedBy: " ")
// Finding a number within an array of words
// There's a problem if there are couple of numbers in the sentence, it returns all of them and not only the needed time.
let numbers = abc.compactMap {
// convert each substring into an Int
return Int($0)
}
for i in 1...100 {
if str.contains(String(i) + " minutes") {
print(i)
}
}
Спасибо за любой из ваша помощь! Я просто сошел с ума от этой задачи на 3 месяца. Также, если что-то непонятно или немного запутано, скажите, пожалуйста! Попробую поправить.