剑指 - 单词长度的最大乘积(Swift)

76 阅读1分钟

题目

输入一个字符串数组words,请计算不包含相同字符的两个字符串words[i]和words[j]的长度乘积的最大值。如果所有字符串都包含至少一个相同字符,那么返回0。假设字符串中只包含英文小写字母。例如,输入的字符串数组words为["abcw","foo","bar","fxyz","abcdef"],数组中的字符串"bar"与"foo"没有相同的字符,它们长度的乘积为9。"abcw"与"fxyz"也没有相同的字符,它们长度的乘积为16,这是该数组不包含相同字符的一对字符串的长度乘积的最大值。

解题思路

  • 异常情况:如果数组为空,直接返回 0 。 
  • 使用 Int32 的其中26位来存储26个小写字母,如果两个单词都包含某个字符,那么该位值为1 ,那么两个数进行与运算不为零。若与运算结果为零则说明两个单词没有任何相同的字符。
  • 首先遍历字符串数组 words,然后内部循环每个字符串来存储当前字符串都包含哪几个字符。binary[index] |= 1 << Int(asci1 - asci2)
  • 然后遍历 binary 每个值与其他值进行与运算,若结果为 0 ,则去 words 获取相应 Index 字符串长度进行乘运算,将乘积与上次结果取最大值。

代码实现

class MaxMutil {
    static func maxMutil(_ words: [String]) -> Int {
        if words.isEmpty {
            return 0
        }
        var binary = Array(repeating: 0, count: words.count)
        
        for index in 0..<words.count {
            for char in words[index] {
                let a: Character = "a"
                if let asci1 = char.asciiValue, let asci2 = a.asciiValue {
                    binary[index] |= 1 << Int(asci1 - asci2)
                }
            }
        }
        
        var result = 0
        for index in 0..<binary.count {
            for innerIndex in (index + 1)..<binary.count {
                if binary[index] & binary[innerIndex] == 0 {
                    result = max(result, words[index].count * words[innerIndex].count)
                }
            }
        }
        return result
    }
}