If you get the image objects from files, you can just send the filenames to the workers and let them open the images themselves.

Otherwise, you can send the image data (with Image.getdata()), along with the size and pixel format, and have the workers reconstruct the image using Image.new() and Image.putdata().

Answer from nneonneo on Stack Overflow
Top answer
1 of 3
3

If you get the image objects from files, you can just send the filenames to the workers and let them open the images themselves.

Otherwise, you can send the image data (with Image.getdata()), along with the size and pixel format, and have the workers reconstruct the image using Image.new() and Image.putdata().

2 of 3
2

Just put the names of the files in a list, and let the worker processes handle them. The example below uses ImageMagick in a subprocess to do some image conversion from an obscure format. But the same principle can be used with PIL. Just replace the contents of the processfile() function. This is a program that I use frequently to convert DICOM files (a format used in medical imaging, from an X-ray machine in this case) to PNG format.

"""Convert DICOM files to PNG format, remove blank areas. The blank erea
   removal is based on the image size of a Philips flat detector. The image
   goes from 2048x2048 pixels to 1574x2048 pixels."""

import os
import sys
import subprocess
from multiprocessing import Pool, Lock

globallock = Lock()

def checkfor(args):
    """Make sure that a program necessary for using this script is
    available.

    Arguments:
    args -- string or list of strings containing a command to test
    """
    if isinstance(args, str):
        args = args.split()
    try:
        f = open('/dev/null')
        subprocess.call(args, stderr=subprocess.STDOUT, stdout=f)
        f.close()
    except:
        print "Required program '{}' not found! exiting.".format(args[0])
        sys.exit(1)

def processfile(fname):
    """Use the convert(1) program from the ImageMagick suite to convert the
       image and crop it.

    Arguments:
    fname -- string containing the name of the file to process
    """
    size = '1574x2048'
    args = ['convert', fname, '-units', 'PixelsPerInch', '-density', '300',
            '-crop', size+'+232+0', '-page', size+'+0+0', fname+'.png']
    rv = subprocess.call(args)
    globallock.acquire()
    if rv != 0:
        print "Error '{}' when processing file '{}'.".format(rv, fname)
    else:
        print "File '{}' processed.".format(fname)
    globallock.release()

def main(argv):
    """Main program.

    Arguments:
    argv -- command line arguments
    """
    if len(argv) == 1:
        # If no filenames are given, print a usage message.
        path, binary = os.path.split(argv[0])
        print "Usage: {} [file ...]".format(binary)
        sys.exit(0)
    # Verify that the convert program that we need is available.
    checkfor('convert')
    # Apply the processfile() function to all files in parallel.
    p = Pool()
    p.map(processfile, argv[1:])
    p.close()

if __name__ == '__main__':
    main(sys.argv)
🌐
GitHub
github.com › python-pillow › Pillow › issues › 2995
Multiprocessing and loading images · Issue #2995 · python-pillow/Pillow
February 5, 2018 - from PIL import Image from multiprocessing import Pool def f(path): return Image.open(path) impath = ['/home/usr/Desktop/img1.jp2', '/home/usr/Desktop/img2.jp2', '/home/usr/Desktop/img3.jp2'] p = Pool() im = p.map(f, impath) But when I try to edit im (e.g. im.getpixel(0,0)) that happens: Traceback (most recent call last): File "<stdin>", line 1, in <module> File "/home/usr/.local/lib/python3.6/site-packages/PIL/Image.py", line 1054, in copy self.load() File "/home/usr/.local/lib/python3.6/site-packages/PIL/Jpeg2KImagePlugin.py", line 198, in load if self.reduce: AttributeError: 'Jpeg2KImageFile' object has no attribute 'reduce' Is that an issue that occurs when working with jp2 images?
🌐
Python
mail.python.org › pipermail › image-sig › 2012-June › 007045.html
[Image-SIG] PIL and multiprocessing module
June 6, 2012 - > > > This is the code I have so far: > def convert_to_gs_load(surf): > width, height = surf.size > pix = surf.load() > > for x in range(width): > for y in range(height): > alpha = 1 > red, green, blue = pix[x, y] > average = (red + green + blue) // 3 > gs_color = (average, average, average, alpha) > pix[x, y] = gs_color > > def convert_to_gs_load_mp(surf): > width, height = surf.size > pix = surf.load() > > t1 = multiprocessing.Process(target=gs_load, args=(pix, width, 0, height / 4)) > t2 = multiprocessing.Process(target=gs_load, args=(pix, width, height / 4, height / 2)) > t3 = multiprocess
People also ask

How are Python multithreading and multiprocessing related?
Both multithreading and multiprocessing allow Python code to run concurrently. Only multiprocessing will allow your code to be truly parallel. However, if your code is IO-heavy (like HTTP requests), then multithreading will still probably speed up your code.
🌐
toptal.com
toptal.com › python › beginners-guide-to-concurrency-and-parallelism-in-python
Python Multithreading and Multiprocessing Tutorial | Toptal®
What's the difference between Python threading and multiprocessing?
With threading, concurrency is achieved using multiple threads, but due to the GIL only one thread can be running at a time. In multiprocessing, the original process is forked process into multiple child processes bypassing the GIL. Each child process will have a copy of the entire program’s memory.
🌐
toptal.com
toptal.com › python › beginners-guide-to-concurrency-and-parallelism-in-python
Python Multithreading and Multiprocessing Tutorial | Toptal®
What is a thread in Python?
A thread is a lightweight process or task. A thread is one way to add concurrency to your programs. If your Python application is using multiple threads and you look at the processes running on your OS, you would only see a single entry for your script even though it is running multiple threads.
🌐
toptal.com
toptal.com › python › beginners-guide-to-concurrency-and-parallelism-in-python
Python Multithreading and Multiprocessing Tutorial | Toptal®
🌐
Python Tutorial
pythontutorial.net › home › python concurrency › python multiprocessing
Python Multiprocessing
June 2, 2023 - Third, modify the program to use multiprocessing. Each process will create a thumbnail for a picture: import time import os from PIL import Image, ImageFilter import multiprocessing filenames = [ 'images/1.jpg', 'images/2.jpg', 'images/3.jpg', 'images/4.jpg', 'images/5.jpg', ] def create_thumbnail(filename, size=(50,50), thumb_dir ='thumbs'): # open the image img = Image.open(filename) # apply the gaussian blur filter img = img.filter(ImageFilter.GaussianBlur()) # create a thumbnail img.thumbnail(size) # save the image img.save(f'{thumb_dir}/{os.path.basename(filename)}') # display a message p
🌐
Python
docs.python.org › 3 › library › multiprocessing.html
multiprocessing — Process-based parallelism
Due to this, the multiprocessing module allows the programmer to fully leverage multiple processors on a given machine.
🌐
LinkedIn
linkedin.com › pulse › intro-multiprocessing-python-part-2-mihai-vlad-stoica
An Intro to Multiprocessing in Python - Part 2
August 16, 2023 - These additional examples showcase the versatility of multiprocessing in Python, covering image processing, progress tracking, data scraping, handling multiple function arguments, and matrix operations. Each example demonstrates how multiprocessing can be applied to different scenarios, providing efficient parallel processing and speeding up execution times. If you are interested in any of the examples that I gave you below, ask in a comment and I can provide more info. ... import multiprocessing from PIL import Image def process_image(image_path): # Load and process the image image = Image.op
🌐
McNeel Forum
discourse.mcneel.com › scripting
Python multiprocessing - Scripting - McNeel Forum
January 13, 2016 - I just started exploring multiprocessing in python outside of ghpythonlib.parallel.run(). I’ve run into some unexpected results. My test script: import multiprocessing as mp import time from PIL import Image as image class myclass: def __init__(self,integer): self.integer=integer self.result=None self.image=None def func(_index): #this function uses PIL to generate a solid color image #the purpose is to cause significant CPU load myclasslist[_index].im...
🌐
GeeksforGeeks
geeksforgeeks.org › python › how-can-we-display-an-image-in-a-child-process-in-python
How can we display an image in a child process in Python - GeeksforGeeks
July 10, 2024 - In this approach, we are using multiprocessing and Tkinter to display an image in a child process. The approach1Fn function creates a Tkinter window (root) and loads an image from image_path using PIL (ImageTk).
Find elsewhere
🌐
Toptal
toptal.com › python › beginners-guide-to-concurrency-and-parallelism-in-python
Python Multithreading and Multiprocessing Tutorial | Toptal®
May 26, 2026 - Now that we have all these images downloaded with our Python ThreadPoolExecutor, we can use them to test a CPU-bound task. We can create thumbnail versions of all the images in both a single-threaded, single-process script and then test a multiprocessing-based solution. We are going to use the Pillow library to handle the resizing of the images.
🌐
Stack Overflow
stackoverflow.com › questions › 67298377 › pil-not-drawing-using-multiprocessing
python - PIL not drawing using multiprocessing - Stack Overflow
April 28, 2021 - from PIL import Image, ImageDraw from mandelbrot import mandelbrot, MAX_ITER import time import threading import multiprocessing from numpy import floor # Image size (pixels) WIDTH = 150*2 HEIGHT = 150*2 t = time.time() # End_Point = [-0.5,0] # End_Zoom = 1.5 End_Point = [-4.556239E-2, -6.824076E-1] End_Zoom = 4.167107E-5 End_Value = [End_Point[0]-End_Zoom, End_Point[0]+End_Zoom, -(End_Point[1])-End_Zoom, -(End_Point[1])+End_Zoom] palette = [] im = Image.new('HSV', (WIDTH, HEIGHT), (0, 0, 0)) draw = ImageDraw.Draw(im) def threadDraw(xPos, yPos,GridNumber): xStart = int(floor(xPos*WIDTH/GridNum
🌐
Kaggle
kaggle.com › code › rsmits › using-multiprocessing-for-image-preprocessing
Using multiprocessing for image preprocessing
Checking your browser before accessing www.kaggle.com · Click here if you are not automatically redirected after 5 seconds
🌐
PyImageSearch
pyimagesearch.com › home › blog › multiprocessing with opencv and python
Multiprocessing with OpenCV and Python - PyImageSearch
December 29, 2022 - In this tutorial, you will learn how to use multiprocessing with OpenCV and Python to perform feature extraction. You’ll learn how to use multiprocessing with OpenCV to parallelize feature extraction across the system bus, including all processors and cores on your computer.
🌐
Pymotw
ja.pymotw.com › 2 › multiprocessing › communication.html
プロセス間通信 - Python Module of the Week
$ python multiprocessing_queue.py Doing something fancy in Process-1 for Fancy Dan! もっと複雑なサンプルとして JoinableQueue からデータを取り出して結果を親プロセスへ返す複数ワーカーを管理する方法を紹介します。 poison pill テクニックはワーカーを停止するために使用されます。実際のタスク設定後、メインプログラムはワーカー毎に “stop” 値をジョブキューへ追加します。ワーカーは特別な値に遭遇したときにその処理ループから脱出します。メインプロセスは、その結果を処理する前に全タスクの終了を待つためにタスクキューの join() メソッドを使用します。
🌐
OneUptime
oneuptime.com › home › blog › how to use multiprocessing for cpu-bound tasks in python
How to Use multiprocessing for CPU-Bound Tasks in Python
January 25, 2026 - import multiprocessing from concurrent.futures import ProcessPoolExecutor import time from pathlib import Path def process_image(image_path): """Simulate CPU-intensive image processing.""" # In real code, this would do actual image processing # using PIL, OpenCV, etc.
🌐
Medium
medium.com › featurepreneur › speeding-up-image-processing-using-multiprocessing-in-python-ceeced8026bf
Speeding up image processing using multiprocessing in Python | by Santhosh Kannan | featurepreneur | Medium
February 3, 2023 - Multi-processing can be implemented by using the built-in multiprocessing module which contains the methods for creating and working with processes. However, an easier way to start a group of processes is by using the ProcessPoolExecutor which ...
🌐
DigitalOcean
digitalocean.com › community › tutorials › python-multiprocessing-example
Python Multiprocessing Example: Process, Pool & Queue | DigitalOcean
March 31, 2026 - Learn Python multiprocessing with hands-on examples covering Process, Pool, Queue, and starmap. Run code in parallel today with this tutorial.
Top answer
1 of 3
7

You cannot speed it up using threading due to the Global Interpreter Lock. Certain internal state of the Python interpreter is protected by that lock, which prevents different threads that need to modify that state from running concurrently.

You could speed it up by spawning actual processes using multiprocessing. Each process will run in its own interpreter, thus circumventing the limitation of threads. With multiprocessing, you can either use shared memory, or give each process its own copy/partition of the data.

Depending on your task, you can either parallelize the processing of a single image by partitioning it, or you can parallelize the processing of a list of images (the latter is easily done using a pool). If you want to use the former, you might want to store the image in an Array that can be accessed as shared memory, but you'd still have to solve the problem of where to write the results (writing to shared memory can hurt performance badly). Also note that certain kinds of communication between processes (Queues, Pipes, or the parameter/return-value passing of some function in the module) require the data to be serialized using Pickle. This imposes certain limitations on the data, and might create significant performance-overhead (especially if you have many small tasks).

Another way for improving performance of such operations is to try writing them in Cython, which has its own support for parallelization using OpenMP - I have never used that though, so I don't know how much help it can be.

2 of 3
1

Take a look at Doug Hellmans tutorial on multiprocessing. As Björn points out, there are various issues regarding parallel processing which you'll need to get a hang of, but it can really be worth the effort.

Tip: You can use multiprocessing.cpu_count() to check the number of cores available to you.

🌐
codestudy
codestudy.net › blog › running-python-on-multiple-cores
Python Multiprocessing: Fix Single Core Usage and Run Your Program on Multiple Cores for Faster Execution — codestudy.net
For the latter, multiprocessing is the key to unlocking multi-core performance. Python’s built-in multiprocessing module (no extra installation required!) enables parallel execution by spawning separate processes instead of threads.
🌐
MachineLearningMastery
machinelearningmastery.com › home › blog › multiprocessing in python
Multiprocessing in Python - MachineLearningMastery.com
June 21, 2022 - Multiprocessing is the ability of a system to run multiple processors at one time. If you had a computer with a single processor, it would switch between multiple processes to keep all of them running.