Home > other >  Reverse Words with exclusion rules like anagrams and numbers
Reverse Words with exclusion rules like anagrams and numbers

Time:07-30

Need some help!

I have a model function in a simple project for reversing words.

The questions is:


First - How can I reverse my words (sentences) to make an anagram? For example, I need to shift the first character in each reversed word on two positions by forward. Example:

Original - Hello world

Reversed with anagrams: - lloeH lrdow


Second - How can I reverse my words (sentences) without numbers inside it? Example:

Original - Hello world 1234

Reversed without numbers - olleH dlrow 1234


How can I do it in my code?

import Foundation

class ReverseWords {
    
    public func reverse(textField: String) -> String {
        
        if textField.isEmpty {
            return ""
        }
        
        return textField.trimmingCharacters(in: .whitespacesAndNewlines)
            .components(separatedBy: " ")
            .map { String ( $0.reversed() ) }
            .joined(separator: " ")
    }
}

CodePudding user response:

It’s helpful to break your problem into independently testable functions.

Here are two functions you should find useful:

func shift2(_ str: String) -> String {
    guard str.length > 2 else { return str }

    let first = str.prefix(1)
    let secondthird = str.prefix(3).suffix(2)
    let end = String(str.dropFirst(3))

    return secondthird   first   end
}

func reverseWord(_ str: String) -> String {
    guard Set(str).intersection(Set("0123456789")).isEmpty else { return str }

    return String(str.reversed())
}

Examples

print(shift2("abcde"))
print(shift2("abc"))
print(shift2("ab"))
bcade
bca
ab
print(reverseWord("Hello"))
print(reverseWord("Hello1"))
print(reverseWord("12345"))
olleH
Hello1
12345

CodePudding user response:

Check this out.

func anagram(sentence: String, separator: Character = " ") -> String {
    sentence
        .trimmingCharacters(in: .whitespacesAndNewlines)
        .split(separator: separator)
        .map { $0.contains(where: { $0.isNumber }) ? String($0) : String($0).reverseAndShift() }
        .joined(separator: String(separator))
}

extension String {
    func reverseAndShift(by offset: Int = 2) -> String {
        var reversed = Array(reversed())

        if let firstElement = reversed.first, offset < reversed.count {
            reversed.removeFirst()
            reversed.insert(firstElement, at: offset)
        }

        return String(reversed)
    }
}

print(anagram(sentence: "Hello world")) -> lloeH lrdow

print(anagram(sentence: "Hello world 1234")) -> lloeH lrdow 1234

CodePudding user response:

I moved the functionality for reversing the string and moving the character into a separate function to streamline the code a bit. The internal function reverses the string and then create a new string from the first two characters, the one to move and the rest of the string

public func reverse(textField: String) -> String {
    func reverseAndMove(_ string: String) -> String {
        guard string.count > 2 else { return "\(string.reversed())" }
        let temp = String(string.reversed().dropFirst())
        return "\(temp[temp.startIndex...temp.index(temp.startIndex, offsetBy: 1)])\(string.last!)\(temp[temp.index(temp.startIndex, offsetBy: 2)..<temp.endIndex])"
    }

    return textField
        .trimmingCharacters(in: .whitespacesAndNewlines)
        .components(separatedBy: " ")
        .map { $0.contains(/"\d"/) || $0.isEmpty ? $0 : reverseAndMove($0) } // or "\\d" for 5.6 or earlier
        .joined(separator: " ")
}

Note that I have ignored punctuation marks here since it wasn't part of the question.

  • Related