优化Swift代码(开关盒)

时间:2014-06-17 21:24:43

标签: switch-statement swift

我是Swift的新手,正在找人帮我优化我的代码..我几乎100%肯定它写得比我在这里做的要聪明得多。这只是一些代码.. Switch将比这长4倍..帮助我以一些简单的方式做到这一点:)

func calc(distance:Int, male:Bool, longhitter:Bool){
    switch (distance,male,longhitter){
    case (237..600,true,true):
        LblResultat.text = Clubs[1]
    case (215..237,true,true):
        LblResultat.text = Clubs[2]
    case (190..215,true,true):
        LblResultat.text = Clubs[3]
    case (170..190,true,true):
        LblResultat.text = Clubs[4]
    case (155..170,true,true):
        LblResultat.text = Clubs[5]
    case (145..155,true,true):
        LblResultat.text = Clubs[6]
    case (135..145,true,true):
        LblResultat.text = Clubs[7]
    case (130..135,true,true):
        LblResultat.text = Clubs[8]
    case (120..130,true,true):
        LblResultat.text = Clubs[9]
    case (110..120,true,true):
        LblResultat.text = Clubs[10]
    case (100..110,true,true):
        LblResultat.text = Clubs[11]
    case (90..100,true,true):
        LblResultat.text = Clubs[12]
    case (80..90,true,true):
        LblResultat.text = Clubs[12]
    default:
        LblResultat.text = "None found"
    }
}

谢谢堆:)

3 个答案:

答案 0 :(得分:2)

我建议使用静态三维查找表。对于距离,您将需要case语句将其转换为索引,或者算术和if-then-else的组合(对于前两种情况,确实如此),或者您可以在排序列表中设置边界点并使用二进制搜索。实际上,您甚至可以将表(单独)生成为600x2x2,并编写一个创建初始化代码的实用程序。也就是说,输出600x2x2表,您可以在静态初始化程序中使用它。

答案 1 :(得分:1)

你的数据气味呈指数曲线,与距离的平方成反比。

我发布了一些只是为了好玩,以防数学方法可能对您有所帮助 - 而且根据事实,我无法猜测是否会这样做你提供了。

我在您的数据上尝试了一些curve fitting,看起来您的x,y数据非常类似于此:

y = round(100000 ^ -2)

现在,由此产生的结果可能会有所不同:

 85     14
 95     12
105     10
115      8
125      7
132      6
140      6
150      5
165      4
180      4
200      3
220      3
400      1
599      1

但我们可以确保他们不会溢出一行代码。

这种方法为您提供了一种非常简单的解决方案编码方式:

func calc(distance:Int, male:Bool, longhitter:Bool) {
    var index: Int?

    switch (male,longhitter){
        case (true, true):
            index = calcIndex(distance, 100_000, -2)
        case (true, false):
            index = calcIndex(distance, 90_000, -2)
        // ...
    default:
        break
    }

    if index {
        LblResultat.text = Clubs[index!]
    }
}

func calcIndex(distance: Int, multiplier: Double, power: Double) -> Int {
    let index = Int(multiplier * pow(Double(distance), power) + 0.5);
    return max(1, min(index, 12))
}

正如您所看到的,您可以"微调"男性,女性,长打者与否的曲线等。

由于您的数据似乎来自物理学,那么为什么不使用数学来构建解决方案:)

答案 2 :(得分:1)

这样的事情怎么样?

func calc2(distance:Int, male:Bool, longhitter:Bool) -> String {
    switch (male, longhitter) {
        case (true, true):
            let posts = [600, 237, 215, 190, 170, 155, 145, 135, 130, 120, 110, 100, 80]
            for i in 0..posts.count - 1 {
                if distance < posts[i] && distance > posts[i + 1] {
                    return clubs[i]
                }
            }
            return "not found"
        case (true, false):
            // when you do have data, do the same thing here
            return "no data"
        case (false, true):
            // when you do have data, do the same thing here
            return "no data"
        case (false, false):
            // when you do have data, do the same thing here
            return "no data"
        default:
            return "wtf?"
    }
}

我将“俱乐部”更改为“俱乐部”,因为我猜它是一个数组,而不是一个类型,我正在返回一个String,而不是将UI依赖关系构建到逻辑中。

如此多的魔术数字硬编码通常是一个坏主意,这样的方法允许您从文件加载数据数组或以后更新它。