Skip to content

Instantly share code, notes, and snippets.

@somada141
Created March 2, 2015 10:30
Show Gist options
  • Star 16 You must be signed in to star a gist
  • Fork 3 You must be signed in to fork a gist
  • Save somada141/8dd67a02e330a657cf9e to your computer and use it in GitHub Desktop.
Save somada141/8dd67a02e330a657cf9e to your computer and use it in GitHub Desktop.
Load DICOM data into a NumPy array with PyDICOM #python #dicom #medical #imagedata #pydicom #fileIO

We start with the imports:

import dicom
import os
import numpy

The pydicom package can be installed through pip and can be found in https://pypi.python.org/pypi/pydicom/

Populate a lstFilesDCM with the filenames of the DICOM files under a given PathDicom directory:

PathDicom = "./dir_with_dicom_series/"
lstFilesDCM = []  # create an empty list
for dirName, subdirList, fileList in os.walk(PathDicom):
    for filename in fileList:
        if ".dcm" in filename.lower():  # check whether the file's DICOM
            lstFilesDCM.append(os.path.join(dirName,filename))

Use the first of the DICOM files to read in some of the metadata, specifically the image dimensions, the pixel-spacing, and the slice-thickness:

# Get ref file
RefDs = dicom.read_file(lstFilesDCM[0])

# Load dimensions based on the number of rows, columns, and slices (along the Z axis)
ConstPixelDims = (int(RefDs.Rows), int(RefDs.Columns), len(lstFilesDCM))

# Load spacing values (in mm)
ConstPixelSpacing = (float(RefDs.PixelSpacing[0]), float(RefDs.PixelSpacing[1]), float(RefDs.SliceThickness))

Load all the pixel data into an appropriate sized NumPy array named ArrayDicom:

# The array is sized based on 'ConstPixelDims'
ArrayDicom = numpy.zeros(ConstPixelDims, dtype=RefDs.pixel_array.dtype)

# loop through all the DICOM files
for filenameDCM in lstFilesDCM:
    # read the file
    ds = dicom.read_file(filenameDCM)
    # store the raw image data
    ArrayDicom[:, :, lstFilesDCM.index(filenameDCM)] = ds.pixel_array

The entire code can be seen in the accompanying .py file

import dicom
import os
import numpy
PathDicom = "./dir_with_dicom_series/"
lstFilesDCM = [] # create an empty list
for dirName, subdirList, fileList in os.walk(PathDicom):
for filename in fileList:
if ".dcm" in filename.lower(): # check whether the file's DICOM
lstFilesDCM.append(os.path.join(dirName,filename))
# Get ref file
RefDs = dicom.read_file(lstFilesDCM[0])
# Load dimensions based on the number of rows, columns, and slices (along the Z axis)
ConstPixelDims = (int(RefDs.Rows), int(RefDs.Columns), len(lstFilesDCM))
# Load spacing values (in mm)
ConstPixelSpacing = (float(RefDs.PixelSpacing[0]), float(RefDs.PixelSpacing[1]), float(RefDs.SliceThickness))
# The array is sized based on 'ConstPixelDims'
ArrayDicom = numpy.zeros(ConstPixelDims, dtype=RefDs.pixel_array.dtype)
# loop through all the DICOM files
for filenameDCM in lstFilesDCM:
# read the file
ds = dicom.read_file(filenameDCM)
# store the raw image data
ArrayDicom[:, :, lstFilesDCM.index(filenameDCM)] = ds.pixel_array
@canbax
Copy link

canbax commented May 21, 2017

Why every slice has a property called SliceThickness? For a 3D image, every slice should have the same thickness to be consistent. Also I heard that slice thickness is based on the machine settings or machine type which takes the CT scan.

@rachanapotpelwar
Copy link

RefDs = dicom.read_file(lstFilesDCM[0])
at this point i m getting error
IndexError: list index out of range

In

@naimavahab
Copy link

Can anyone tell what is this error is .. AttributeError: Dataset does not have attribute 'PixelSpacing'.

@Acedorkz
Copy link

Have the same problem "Dataset does not have attribute 'PixelSpacing'"...

@IsraelBorges
Copy link

I have the same problems to load dicom images in python. Can anyone help me?

@ZhangYuef
Copy link

I bumped into the same problem as @naimavahab mentioned.

@radhika98ravi
Copy link

i used the same code but it gives " Dataset has no attribute Pixel Spacing"

@suriya18
Copy link

How to overcome this error ?
6 ds = pydicom.read_file(filenameDCM)
7 # store the raw image data
----> 8 ArrayDicom[:, :, lstFilesDCM.index(filenameDCM)] = ds.pixel_array

ValueError: could not broadcast input array from shape (552,474) into shape (512,512)

@somada141
Copy link
Author

@suriya18 this means that ArrayDicom has the wrong dimensions. You've clearly made it at 512x512x but your DICOM's dimensions are 552x474x

@Naeemmariam7
Copy link

This code returns a 2D array, How can I get 3D array?

@somada141
Copy link
Author

The code should return a 3D array by stacking the 2D dicom slices as you can see in the final loop. If you're only getting a 2D array that must mean that your path-walk only returned a single file. Have you checked that your filenames are retrieved correctly?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment