简体   繁体   English

for循环跳过数组中的第一个字符串

[英]for loop skipping first string in array

I currently have an issue in my script where I use a for loop to iterate through an array of elements and check for their existence in the GUI. 目前,我的脚本中存在一个问题,其中我使用了一个for循环来遍历元素数组并检查它们是否存在于GUI中。 My issue is the for loop always skips the first entry of the array. 我的问题是for循环总是跳过数组的第一项。

My current script is as follows: 我当前的脚本如下:

public class GUIFunctionality {
    static Properties config = Data.getProperties("config");
    static int Pass = 0;
    static Screen s = new Screen();

    @Test(priority = 0)
    public static void loginGUI() {
        WebDriver driver = AutomationWebDriver.getWebDriver("firefox", config.getProperty("url"));

        // Test all GUI elements on login screen.

        String[] login_elements = { "loginbutton.png", "logintitle.png", "smalllogo.png", "remembermechecked.png",
                "signupbutton.png", "signuptitle.png", "changelanguage.png" };
        ArrayList<String> passed = new ArrayList<String>();
        ArrayList<String> failed = new ArrayList<String>();

        for (String base : login_elements) {
            String file = String.format("imagerepo/config/%s", base);
            if (s.exists(file) != null) {
                System.out.println(file + " has been successfully found.");
                passed.add(file);
                Pass++;
            } else {
                System.out.println(file + " has not been found.");
                failed.add(file);
            }
        }

This script completely ignores "loginbutton.png" , almost as though it never existed in the script at all. 该脚本完全忽略了"loginbutton.png" ,仿佛它根本不存在于脚本中。 I'm really stumped as to why. 我真的很困惑为什么。 Here is the console output: 这是控制台输出:

imagerepo/config/logintitle.png has been successfully found.
imagerepo/config/smalllogo.png has been successfully found.
imagerepo/config/remembermechecked.png has been successfully found.
imagerepo/config/signupbutton.png has been successfully found.
imagerepo/config/signuptitle.png has been successfully found.
imagerepo/config/changelanguage.png has been successfully found.
Found elements: [imagerepo/config/logintitle.png, imagerepo/config/smalllogo.png, imagerepo/config/remembermechecked.png, imagerepo/config/signupbutton.png, imagerepo/config/signuptitle.png, imagerepo/config/changelanguage.png]
Missing elements: []

I'm wondering what I need to alter so the first entry of the String[] login_elements is included in the for loop. 我想知道我需要更改什么,以便String[] login_elements的第一项包含在for循环中。 What's also interesting is that adding one more entry to the String[] login_elements will completely fix it. 有趣的是,在String[] login_elements再添加一个条目将完全解决该问题。

Making this minor change: (nobutton.png is an image that exists within the repository, but not on the page under test) 进行较小的更改:(nobutton.png是存储库中存在的图像,但在被测页面上不存在)

String[] login_elements = { "nobutton.png", "loginbutton.png", "logintitle.png", "smalllogo.png",
                "remembermechecked.png", "signupbutton.png", "signuptitle.png", "changelanguage.png" };

This one change will now print this to the console: 现在,这一更改将打印到控制台:

imagerepo/config/nobutton.png has not been found.
imagerepo/config/loginbutton.png has been successfully found.
imagerepo/config/logintitle.png has been successfully found.
imagerepo/config/smalllogo.png has been successfully found.
imagerepo/config/remembermechecked.png has been successfully found.
imagerepo/config/signupbutton.png has been successfully found.
imagerepo/config/signuptitle.png has been successfully found.
imagerepo/config/changelanguage.png has been successfully found.
Found elements: [imagerepo/config/loginbutton.png, imagerepo/config/logintitle.png, imagerepo/config/smalllogo.png, imagerepo/config/remembermechecked.png, imagerepo/config/signupbutton.png, imagerepo/config/signuptitle.png, imagerepo/config/changelanguage.png]
Missing elements: [imagerepo/config/nobutton.png]

This console output includes every entry within that array. 该控制台输出包括该阵列内的每个条目。 Deleting "nobutton.png", from the array will bring us back to our original issue. 从数组中删除“ nobutton.png”将使我们回到原始问题。

So what the heck is going on? 那么到底发生了什么? The only thing I can possibly think of is a minimum number of strings in an array to include the first entry, but that just seems downright silly. 我唯一能想到的就是数组中包含第一个条目的最小字符串数,但这看起来简直是愚蠢的。

Edit : s.exists(String) is an instance of the Sikuli screen using the exists function to check for the existance of elements on the page. 编辑s.exists(String)是的一个实例Sikuli使用屏幕exists功能检查页面上的元素是否存在等。 I really do not think this has anything to do with the error. 我真的认为这与错误无关。 I also could be completely wrong about this. 我对此也可能是完全错误的。 I've learned most of the Sikuli library through trial-and-error (time-crunch around release dates is a horrible thing), so my ignorance on "why" is pretty high, which is why I'm here. 我已经通过反复试验学习了大部分Sikuli库(发布日期的时间紧迫是一件可怕的事情),所以我对“为什么”的无知非常多,这就是为什么我在这里。

Edit : Remember, adding one more entry to the array completely fixes the problem. 编辑 :请记住,向数组添加一个以上条目可以完全解决该问题。

Edit : Added the instance of s . 编辑 :添加了s的实例。 The line WebDriver driver = AutomationWebDriver.getWebDriver("firefox", config.getProperty("url")); WebDriver driver = AutomationWebDriver.getWebDriver("firefox", config.getProperty("url"));WebDriver driver = AutomationWebDriver.getWebDriver("firefox", config.getProperty("url")); is an instance of a Selenium WebDriver I use to start the instance of WebDriver which I have to use alongside Sikuli because our web application is fubar (6 years of legacy code). 是Selenium WebDriver的实例,我用来启动WebDriver的实例,我必须与Sikuli一起使用,因为我们的Web应用程序是富巴(6年的旧代码)。

Another Edit : Source code for Region.exists() method and documentation. 另一个EditRegion.exists()方法和文档的源代码。

Source Code 源代码

Documentation 文献资料

This question has been answered. 这个问题已经回答。 @Berger and @Andy Thomas have also provided some insight into what happens with the loop : @Berger和@Andy Thomas还提供了一些有关循环发生的见解

I think I have found the source code. 我想我已经找到了源代码。 exists uses a while loop based on a timeout value, among other things, so a subsequent call with the same parameter, could well return another result, see : https://github.com/RaiMan/SikuliX-2014/blob/master/API/src/main/java/org/sikuli/script/Region.java - @Berger 存在基于超时值的while循环等,因此具有相同参数的后续调用很可能会返回另一个结果,请参见: https : //github.com/RaiMan/SikuliX-2014/blob/master/ API / src / main / java / org / sikuli / script / Region.java-@Berger

I see from another Sikuli source file that the default autoWaitTimeout is 63 seconds, making the race condition easy to observe. 我从另一个Sikuli源文件中看到,默认的autoWaitTimeout为63秒,这使竞争状况易于观察。 Two important lessons from this question are: 1) A default case is frequently useful, especially if it's not expected to occur -- and 2) If you want a single return value, make a single call. 这个问题有两个重要的教训:1)默认情况经常有用,尤其是在不希望发生这种情况的情况下; 2)如果要使用单个返回值,请进行一次调用。 - @Andy Thomas -@安迪·托马斯

You don't have a default case. 您没有默认情况。 You're using an if-elseif rather than an if-else. 您使用的是if-elseif而不是if-else。

for (String base : login_elements) {
  String file = String.format("imagerepo/config/%s", base);
  if (s.exists(file) != null) {
    ...
  } else if (s.exists(file) == null) {
    ...
  }
}

Your second condition includes a second call to s.exists(file) . 您的第二个条件包括对s.exists(file)的第二次调用。 If neither branch is entered, the value returned must be changing between calls. 如果未输入任何分支,则返回的值必须在两次调用之间更改。

You could handle this by adding a default case. 您可以通过添加默认案例来解决此问题。 An easy way would be to eliminate the second condition. 一种简单的方法是消除第二个条件。

for (String base : login_elements) {
  String file = String.format("imagerepo/config/%s", base);
  if (s.exists(file) != null) {
    ...
  } else {
    ...
  }
}

A debugger can help you find problems like this. 调试器可以帮助您找到类似的问题。 If you set a breakpoint on the first condition, you'd see that the first file is being considered by the loop. 如果在第一个条件上设置断点,则会看到循环正在考虑第一个文件。

This is because you are not facing all possibilities: 这是因为您没有面对所有可能性:

if (s.exists(file) != null) {
    System.out.println(file + " has been successfully found.");
    passed.add(file);
} else {
    System.out.println(file + " has not been found.");
    failed.add(file);
} 

Will throw an error with your same code... 使用相同的代码将引发错误...

I believe the Java code should be: 我相信Java代码应该是:

String[] login_elements = {
    "loginbutton.png",
    "logintitle.png",
    "smalllogo.png", 
    "remembermechecked.png",
    "signupbutton.png",
    "signuptitle.png",
    "changelanguage.png"
};

ArrayList<String> passed = new ArrayList<String>();
ArrayList<String> failed = new ArrayList<String>();

for (String base : login_elements) {
    String file = String.format("imagerepo/config/%s", base);
    File s = new File(file);
    if (s.exists()) {
        System.out.println(file + " has been successfully found.");
        passed.add(file);
    }
    else {
        System.out.println(file + " has not been found.");
        failed.add(file);
    }
}

System.out.println("Found elements: " + passed);
System.out.println("Missing elements: " + failed);

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM