【问题标题】:Modifying try-catch statements to reduce clunky code修改 try-catch 语句以减少笨重的代码
【发布时间】:2015-10-03 05:00:21
【问题描述】:

我一直在与 SikuliX 合作尝试一些 ATDD。当只有 是使用它的人时,该代码运行良好。然而,将下面的代码转移给其他人只会适得其反,无论我对代码的评论如何。

int numOfTries;
while (!isFinishStage && numOfTries != 3) {
                numOfTries++;
                try {
                    temp = new Pattern("imgs/img1.png").similar(0.9f);
                    s.wait(temp, 1);
                    s.find(temp);
                    s.hover(temp);
                    isFinishStage = true;
                    break;
                }catch (FindFailed ff1) {
                    try {
                    temp = new Pattern("imgs/img2").similar(0.5f);
                    s.wait(temp, 1);
                    s.find(temp);
                    s.hover(temp);
                    isFinishStage = true;
                    break;
                } catch (FindFailed ff2) {
             try{
                    temp = new Pattern("imgs/img3");
                    s.wait(temp, 1);
                    s.find(temp);
                    s.click(temp);
                } catch (FindFailed ff3) {
                    continue;
             }
        }
    }
}

一旦图案/图像无法与屏幕上的任何内容匹配(相似性只是调整容差级别),就会引发FindFailed 异常。对于它正在自动化的当前 GUI,有三种可能的场景(这段代码发挥作用的地方)

  1. 屏幕 A 弹出
  2. 屏幕 B 弹出
  3. 1 或 2 都没有,而是弹出“下一步”

因此我们检查Screen A,如果不是,我们检查Screen B,如果不是,我们检查Next,如果不是,重复循环直到我们超过尝试次数——意味着测试失败。

根据 Sikuli 的工作方式或至少我一直在解释它的方式,您将不得不通过多个 try-catch 语句执行各种循环,这似乎有点不妥。

PS:上述代码背后的想法是让它工作。如果有任何歧义,请告诉我,以便我澄清。

【问题讨论】:

  • 到底是什么问题?此代码是否有效?
  • @JamesWierzba - 它确实如预期的那样,但是会导致性能显着下降(我现在可以接受)并且非常不友好地传递给其他人工作。
  • 如果它有效,为什么要修复它?代码并非无法阅读。添加一些类似于你在问题中所说的cmet。
  • @JamesWierzba - 因为虽然此时性能下降和可读性问题是可以接受的,但一旦脚本的大小和复杂性/案例变得更大,就不会这样了。
  • 当代码不可读时,重命名。不要添加 cmets 来弥补错误的命名。 temp 是个坏名字。 FindFailed 是一个坏名字(它甚至不以 Exception 结尾?你怎么能抛出它?) numOfTries 是一个坏名字(只输入数字)。 s 是一个非常糟糕的名字。

标签: java sikuli sikuli-script


【解决方案1】:

以下代码(我认为)等同于您的代码:

int numOfTries;
while (!isFinishStage && numOfTries < 3) {
    numOfTries++;
    if (tryPattern(s, "imgs/img1.png", 0.9f) ||
        tryPattern(s, "imgs/img2", 0.5f)) {
        isFinishStage = true;
    } else {
        // Note that the third "attempt" is inconsistent with
        // the others because you don't set isFinishedStage.
        tryPattern(s, "imgs/img3", 1.0f)
    }
}

private boolean tryPattern(SomeClass s, String path, float similarity) {
    try {
        Pattern temp = new Pattern(path);
        if (similarity != 1.0f) {
            temp = temp.similar(similarity);
        }
        s.wait(temp, 1);
        s.find(temp);
        s.hover(temp);
        return true;
    } catch (FindFailed ff) {
        return false;
    }
}

【讨论】:

  • 这正是我所希望的。真的很喜欢这种设置,明天将使用相同的方法。谢谢@Stephen C
【解决方案2】:

我希望你在课后阅读软件原理并让你的代码变得干净:

10 Object Oriented Design Principles

在此之后,您应该了解 DRY 和 KISS 原则等基础知识,它们应该很好地融入您发布的代码中。

【讨论】:

    【解决方案3】:

    方法如下:

    String [] patterns = {
        "imgs/img1",
        "imgs/img2",
        "imgs/img3"
    };
    
    float [] similarities = {
        0.9f,
        0.5f,
        0.1f
    };
    
    for(int i=0; i<patterns.length; i++) {
        String str = patterns[i];
        try {     
            float sim = 0.1; // default
            try {
                sim = similarities[i];
            } catch (IndexOutofBoundsException e) {;}     
            temp = new Pattern(str).similar(sim);
            s.wait(temp, 1);
            s.find(temp);
            s.hover(temp);
            if(i != patterns.length - 1){ // Different last case
                isFinishStage = true;
                break;
            }
        } catch (FindFailed ff) {
            continue;
        }
    }
    

    【讨论】:

    • 我也很喜欢这个,也打算试一试。干得好:-)
    • 再次感谢您的宝贵时间
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2018-10-14
    • 2011-01-06
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-06-18
    • 1970-01-01
    相关资源
    最近更新 更多