Почему этот код работает так медленно?

1

Я пытаюсь использовать эти методы, чтобы найти цвет в прямоугольной области на экране. Однако иногда на экране появляются миллионы пикселей, и на данный момент я получаю только около 35 итераций getColor. В моем коде должно быть что-то, заставляющее это работать очень медленно.

Как сканировать мой экран быстрее, чем это? В идеале я бы хотел отсканировать весь экран за цвет менее чем за секунду, а не через 8 часов: P

Вот мои два метода.

public static int getColor(int x, int y){
    try{
        return(robot.getPixelColor(x, y).getRGB() * -1);
    }catch(Exception e){
        System.out.println("getColor ERROR");
        return 0;
    }
}

//returns first instance of color,
//Begins top left, works way down to bottom right
public static Point findColor(Box searchArea, int color){
    System.out.println("Test");
    if(searchArea.x1 > searchArea.x2){
        int temp = searchArea.x1;
        searchArea.x1 = searchArea.x2;
        searchArea.x2 = temp;
    }
    if(searchArea.y1 > searchArea.y2){
        int temp = searchArea.y1;
        searchArea.y1 = searchArea.y2;
        searchArea.y2 = temp;
    }
    for(int i = searchArea.x1;i <=searchArea.x2; i++){
        for(int j = searchArea.y1;j<=searchArea.y2;j++){
            if(getColor(i, j) == color){
                return new Point(i, j);

            }
            System.out.println(i + " " + j);
        }
    }
    return new Point(-1, -1);
}
  • 1
    может потому что это рекурсивная функция?
  • 0
    Э-э-э ... Я только что пробовал цикл for до миллиона, печатая каждое число, как только оно появилось, и это все еще занимало целую минуту, чтобы завершиться. Как я могу это сделать, если мой компьютер (AMD FX-6300) не может даже достаточно быстро обработать пробел для цикла?
Показать ещё 7 комментариев
Теги:
performance
awt
awtrobot

2 ответа

4
Лучший ответ

Robot#getColor будет очень медленным, особенно при использовании таким образом.

Лучшим решением было бы захватить снимок экрана (даже в небольших кусках) и обработать полученный BufferedImage.

Используя следующий пример, я получил...

Took 0 seconds to scan image
Took 3 seconds to scan screen

Для области 10x10

Пример кода...

import java.awt.AWTException;
import java.awt.Point;
import java.awt.Rectangle;
import java.awt.Robot;
import java.awt.image.BufferedImage;
import java.util.concurrent.TimeUnit;
import java.util.logging.Level;
import java.util.logging.Logger;

public class TestColorGrab {

    private static Robot robot;

    public static void main(String[] args) {
        try {
            robot = new Robot();
        } catch (AWTException ex) {
            Logger.getLogger(TestColorGrab.class.getName()).log(Level.SEVERE, null, ex);
        }
        new TestColorGrab();
    }

    public TestColorGrab() {
        Rectangle bounds = new Rectangle(0, 0, 10, 10);
        long start = System.currentTimeMillis();
        scanImageArea(bounds);
        System.out.println("Took " + ((System.currentTimeMillis() - start) / 1000), TimeUnit.SECONDS) + " seconds to scan image");

        start = System.currentTimeMillis();
        scanRobotArea(bounds);
        System.out.println("Took " + ((System.currentTimeMillis() - start) / 1000) + " seconds to scan screen");
    }

    public static int getColor(int x, int y) {
        try {
            return (robot.getPixelColor(x, y).getRGB() * -1);
        } catch (Exception e) {
            System.out.println("getColor ERROR");
            return 0;
        }
    }

    public static void scanRobotArea(Rectangle searchArea) {
        for (int i = searchArea.x; i < searchArea.x + searchArea.width; i++) {
            for (int j = searchArea.y; j < searchArea.y + searchArea.height; j++) {
                getColor(i, j);
            }
        }
    }

    public static void scanImageArea(Rectangle searchArea) {
        BufferedImage image = robot.createScreenCapture(searchArea);
        for (int x = 0; x < image.getWidth(); x++) {
            for (int y = 0; y < image.getHeight(); y++) {
                image.getRGB(x, y);
            }
        }
    }

}
  • 0
    10500 секунд для сканирования? Я надеюсь, что это опечатка: P Это должно работать ОЧЕНЬ лучше, хотя, я возьму это с собой и посмотрю, смогу ли я довести его до требуемого уровня эффективности, спасибо!
  • 0
    31000 секунд для сканирования 10х10?
Показать ещё 3 комментария
2

Выньте отпечаток. Вы пишете на консоль миллион раз.

  • 0
    Разница в тестировании, одна секунда ...
  • 0
    Сканирование 50x50 заняло 76 секунд с печатью, 49 секунд без. Я думаю, что MadProgrammer обнаружил самую большую проблему, но приятно знать, что я не могу включать заявления о печати при тестировании эффективности

Ещё вопросы

Сообщество Overcoder
Наверх
Меню