【问题标题】:Enum String values - Binary Operator cannot be applied to operands of type Bool and String枚举字符串值 - 二进制运算符不能应用于 Bool 和 String 类型的操作数
【发布时间】:2015-12-19 07:07:47
【问题描述】:
enum DeviceiPad: String {
    case iPadAir = "iPadAir"
    case iPadAir2 = "iPadAir2"
}

func adjustFontsForDevices() {
    let modelName = UIDevice.currentDevice().modelName

    //iPad size adjustments
    guard modelName == DeviceiPad.iPadAir.rawValue ||
        DeviceiPad.iPadAir2.rawValue 
        else {return}
    do {
        adjustCountTitles()
        }

modelName 调用一个字符串。我想检查该字符串是否与两个枚举原始值(也是字符串)中的任何一个匹配。

由于某种原因,Xcode 抛出了这个错误:

  • 如果您不熟悉guard,请不要让您抛弃它。错误与if 相同
  • guard 在只有一个字符串值时有效。添加第二个会引发错误。

一直在努力弄清楚为什么它将字符串值视为 Bool。也搜索了一下,但在其他地方没有看到这个问题。

有什么想法吗?

【问题讨论】:

  • 你需要的是一个开关
  • 对于投反对票的人,请提供理由。搜索了一下,没有找到答案。认为它可能对其他人有帮助。
  • 谢谢,里奥。当我为任何条件运行相同的方法调用时,开关会进一步复制代码。我是开关的粉丝,但不认为这是他们适合的地方。
  • 这不是真的。您可以将多个案例条件分组在一个案例中
  • 在下面实现了你的建议,Leo。

标签: ios swift enums


【解决方案1】:

小修复

首先

let modelName = UIDevice.currentDevice().modelName

变成这样

let modelName = UIDevice.currentDevice().model

回答

下一个

guard modelName == DeviceiPad.iPadAir.rawValue || DeviceiPad.iPadAir2.rawValue else { return }

变成这样

guard modelName == DeviceiPad.iPadAir.rawValue || modelName == DeviceiPad.iPadAir2.rawValue else { return }

更新:测试您的 modelName 是否为 DeviceiPad 的值

看看下面的评论,你问如何快速检查 modelName 是否是 DeviceiPad 的值。

当然你想要一些东西来避免这个

guard
    modelName == DeviceiPad.iPadAir.rawValue ||
    modelName == DeviceiPad.iPadAir2.rawValue ||
    modelName == DeviceiPad.iPadMini.rawValue ||
    modelName == DeviceiPad.iPadMini2.rawValue ||
    modelName == DeviceiPad.iPadMini3.rawValue ||
    modelName == DeviceiPad.iPadMini4.rawValue else { return }

你可以简单地写

guard let model = DeviceiPad(rawValue: modelName) else { return }

在这种情况下,如果modelName 确实代表DeviceiPad 的原始值,则创建枚举值并执行下一行。否则将执行 else 块。

【讨论】:

  • 嗯。在== 之后没有办法进行逻辑或吧?
  • 就您的“首先”而言,我使用的是扩展程序,所以这无关紧要。不过还是谢谢。
  • || 后面可以有一个逻辑表达式(我的意思是布尔值)。但是在你的代码中你把这个DeviceiPad.iPadAir2.rawValue放在||之后,这是一个String,而不是Bool
  • 好吧,有道理。希望不必重复modelName ==,因为它已被重复使用。但似乎这是不可能的。感谢您的帮助。
  • 将此扩展到更大的枚举,不得不重复似乎有点愚蠢。唉。 guard modelName == DeviceiPad.iPadAir.rawValue || modelName == DeviceiPad.iPadAir2.rawValue || modelName == DeviceiPad.iPadMini.rawValue || modelName == DeviceiPad.iPadMini2.rawValue || modelName == DeviceiPad.iPadMini3.rawValue || modelName == DeviceiPad.iPadMini4.rawValue
【解决方案2】:

我不是一个快速的程序员,但我看到了:

guard modelName == DeviceiPad.iPadAir.rawValue ||
    DeviceiPad.iPadAir2.rawValue 

不应该是这样的

guard modelName == DeviceiPad.iPadAir.rawValue ||
    modelName == DeviceiPad.iPadAir2.rawValue 

您不能简单地使用x == y || z,因为z 本身不是一个布尔值。也就是说,语句如下所示:(x == y) || zz 完全是孤独的,没有任何东西可以与之相比。有些语言确实允许,但大多数不允许。

【讨论】:

  • 是的 appzYourLife 建议如下。希望不必复制modelName == 部分。但似乎做不到。
  • 不。至少,不是在 swift 中(或大多数类似 C 的语言。Python 允许这样做)。
  • 啊。今天学到了一些东西。
  • that 就是 Stack Exchange 的用途。 ;)
【解决方案3】:

如果您只想清理 if 语句,并且对这些设备类型进行了逻辑分组,您可以在 DeviceiPad 枚举上添加一个静态方法。

enum DeviceiPad:String {
    case iPadAir  = "iPadAir"
    case iPadAir2 = "iPadAir2"
    case iPad1 = "iPad"

    static func isSpecialDevice(modelName:String) -> Bool
    {
        guard let model = DeviceiPad(rawValue: modelName) else
        {
            return false
        }

        switch model
        {
        case iPadAir, iPadAir2:
            return true
        default:
            return false
        }
    }
}

然后你就可以使用:

guard DeviceiPad.isSpecialDevice(modelName) else
{
   return
}

【讨论】:

  • 你的isSpecialDevice func 也可以是一个computed property,像这样定义var isSpecial: Bool { return [iPadAir, iPadAir2].contains(self) }
  • OP 必须首先成功地将 modelName 字符串转换并绑定到枚举类型,否则,这是对枚举案例进行分组的一种非常好的和干净的方式。
  • 是的,enum 之外的代码看起来像这样if DeviceiPad(rawValue: modelName)?.isSpecial { ... }
【解决方案4】:

为了比较,我简化了上面的代码。但是使用更大的枚举,我在上面的Leo Dabus' 建议中尝试了一个开关。它可以工作并且相当干净,所以我想我会在这里添加它作为一个选项,因为它可以很好地处理更大的枚举列表并允许不同的情况......

    switch modelName {
    case DeviceiPad.iPadAir.rawValue,
    DeviceiPad.iPadAir2.rawValue,
    DeviceiPad.iPadMini.rawValue,
    DeviceiPad.iPadMini2.rawValue,
    DeviceiPad.iPadMini3.rawValue,
    DeviceiPad.iPadMini4.rawValue:
        adjustCountTitles()
    case DeviceiPad.iPadPro.rawValue:
        adjustCountNumbers()
    default: break
    }

【讨论】:

    猜你喜欢
    • 2021-12-13
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-09-10
    • 1970-01-01
    • 2021-03-04
    相关资源
    最近更新 更多