【问题标题】:When I add more threads the processing time increases?当我添加更多线程时,处理时间会增加吗?
【发布时间】:2013-12-13 11:48:40
【问题描述】:

我正在并行执行图像处理程序,我有 4 个内核,所以当我在少于 5 个线程上运行程序时,应该比仅在 1 个线程上运行时有所改进,我想没有任何改进,因为图片可能太小,因此线程会产生开销。所以我使用 8142x2175 图像仍然没有任何改进。问题可能出在 Eclipse 上吗?

这是我的图像处理程序的主要部分,我包括其中一个类,如您所见,我正在使用 Java 并在 eclipse 上运行它。

public class Main {
    public static void main(String[] args) throws IOException {

        final File imageFile= new File ("C:\\Users\\user\\Desktop\\Parallel\\pic8142x2175.jpg");
        BufferedImage orgImg= ImageIO.read(imageFile);

        // the destination buffered image
        BufferedImage destImg = new BufferedImage(orgImg.getWidth(), orgImg.getHeight(),
                        BufferedImage.TYPE_INT_RGB);

        // let the user enter number of thread
        System.out.println(" please enter number of threads");
        Scanner in = new Scanner(System.in);
        int nThreads=in.nextInt();

        // create the threads
        ExecutorService executor = Executors.newFixedThreadPool(nThreads);

        // assign each thread with its own runnable
        for (int i=0; i<nThreads;i++){

            //Runnable gsr = new GreyscaleRunnable(orgImg, i, nThreads,destImg);
            //Runnable pr = new PixelateRunnable(orgImg,20,i,nThreads,destImg);
            Runnable fr= new FlipRunnable(orgImg,i,nThreads,destImg);
              executor.execute(fr);

          }// end of for loop

        // This will make the executor accept no new threads
        // and finish all existing threads in the queue
        executor.shutdown();
        // Wait until all threads are finish


    }

}

FlipRunnable 类

public class FlipRunnable implements Runnable{

    private BufferedImage img;
    private BufferedImage dest;
    private int my_rank, thread_count;

    // constructor of the class
        public FlipRunnable(BufferedImage img,int my_rank,int thread_count,BufferedImage dest) {
            this.img=img;
            this.my_rank=my_rank;
            this.thread_count=thread_count;
            this.dest=dest;
        }

        long startTime = System.currentTimeMillis();

    @Override
    public void run() {

        int localRows = img.getHeight() / thread_count;
        int myFirstRow = my_rank * localRows;
        int myLastRow = (my_rank + 1) * localRows - 1;

        for (int i = myFirstRow; i <= myLastRow; i++) {
            for (int j = 0; j < img.getWidth(); j++){

                int px = img.getRGB(j, i);

                dest.setRGB(img.getWidth() - j - 1, i, px);


            }// end of j loop

        }// end of i loop

        String dstName = "C:\\Users\\user\\Desktop\\Parallel\\funFlipped.jpg";
        File dstFile = new File(dstName);
        try {
            ImageIO.write(dest, "jpg", dstFile);
        } catch (IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }

        System.out.println("Output image: " + dstName);

        // the total time
        long endTime = System.currentTimeMillis();
        long totalTime = endTime - startTime;
        System.out.println("time is:"+totalTime);
    }

}

【问题讨论】:

  • 首先,您的每个工人似乎都覆盖了目标图像...
  • 另外,setRGB()synchronized,所以工人之间肯定有很多争用。似乎你最好将图像复制到普通数组并在那里工作。
  • 是的,我希望工作人员相互覆盖,这样我就可以获得整个图像的输出,而不仅仅是线程正在处理的部分。对不起我的英语,我想说的是当我没有让工人覆盖时,我的输出只是图像的一部分,这样我就可以完成整个图像
  • @VictorSorokin 是对的。此外,如果您想真正加快使用踏板的速度,您应该利用您的处理器内核。为此,您应该使用 Fork/Join 框架。如果你不这样做,你最终会在线程之间切换处理器,这会减慢你的操作
  • 我认为这个question 已经存在了。

标签: java parallel-processing


【解决方案1】:

我想几乎没有改进是因为setRGB()synchronized 方法,所以工作线程之间存在很多争用。您需要将图像数据复制到数组并在那里工作。

【讨论】:

    【解决方案2】:

    随着线程数量的增加,操作系统在线程之间切换上下文需要付出更多努力。

    理想情况下,线程数不应大于Runtime.getRuntime().availableProcessors()。这通常会返回 CPU 内核的数量(超线程将返回每个内核 2 个线程)。

    【讨论】:

      【解决方案3】:

      首先,您正在尝试处理来自所有线程的相同图片! Shure 的性能不会有任何提升,因为您在同步的 dest.setRGB(...) 中遇到了瓶颈。

      编辑:@Victor Sorokin 在 cmets 中的问题是正确的。

      【讨论】:

      • 如果线程之间没有争用或争用很少,并且您不创建冗余线程(即数量线程数不超过 CPU 内核数)。另外,数据的大小不能太小,这样线程切换就会扼杀任何性能提升。但对于 OP 数据大小,情况并非如此。
      • @Victor Sorokin,啊,好的,我明白了!然后,正如您所说,在 dest.setRGB() 中同步是瓶颈。
      猜你喜欢
      • 1970-01-01
      • 2015-01-08
      • 1970-01-01
      • 2013-12-16
      • 2015-07-02
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多